Bash 快捷操作

GUN Bash 是现代操作系统一般都默认自带的 Shell,它兼容 sh 并提供了更多的 feature,如果我们常用命令行那么记住一些快捷键和 trick 能大大提高我们的工作效率,这篇文章就介绍下本人常用的快捷键和一些技巧。

Bash 默认的是 emacs 模式,这里的快捷键以默认的为准,可以使用set -o命令查看,使用set -o emacs设置。

移动光标

快捷键 描述
Ctrl + a 移动光标到行首
Ctrl + e 移动光标到行尾
Alt + b 移动光标后退一个单词(词首)
Alt + f 移动光标前进一个单词(词首)
Ctrl + f 光标前进一个字母
Ctrl + b 光标后退一个字母
Ctrl + xx 当前位置与行首之间光标切换

一般配合Ctrl的是单字符移动,Alt是单词为边界。建议将键盘上的caps lock键改成Ctrl这样手指移动距离更短按起来也更加舒服方便。

剪切(删除)粘贴

快捷键 描述
Ctrl + k 剪切从光标到行尾
Ctrl + u 剪切从光标到行首
Ctrl + w 从光标向前剪切一个单词
Alt + Backspace 与 Ctrl + w 类似,但分隔符是一些特殊字符
Alt + d 从光标向后剪切一个单词
Ctrl + d 删除光标下一个字母,如果没有字符存在,ctrl+d 则会登出该会话
Ctrl + h 删除光标前一个字母
Alt + t swap(当前单词, 上一个单词)
Ctrl + t swap(当前字母, 上一个字母)
Ctrl + y 粘贴上一次剪切的文本,配合 Ctrl-u、Ctrl-k 效果极好

大小写转换

快捷键 描述
Alt + c 大写当前字母,并移动光标到单词尾
Alt + u 大写从当光标到单词尾
Alt + l 小写从当光标到单词尾

历史命令

快捷键 描述
Ctrl + r 向后搜索历史命令
Ctrl + g 退出搜索
Ctrl + p 历史中上一个命令,代替向上方向键
Ctrl + n 历史中下一个命令,代替乡下方向键
Alt + . 上一个命令的最后一个单词

终端指令

快捷键 描述
Ctrl + l 跳纸,换页,清屏
Ctrl + m 回车(Carriage return)
Ctrl + s 停止输出(在 Zsh 中为向前搜索历史命令)
Ctrl + q 继续输出
Ctrl + c 终止当前命令
Ctrl + z 挂起当前命令
Ctrl + d 结束输入(产生一个 EOF)

Bang (!) 命令

快捷键 描述
!n 执行第 n 条命令
!-n 执行倒数第 n 条命令
!xx 执行最近的以 xx 开头的命令
!xx:p 和上面一样,但仅打印输出,而不执行命令
!! 执行上一条命令, 与 !-1 相同
!$ 上一条命令的最后一个参数,与 Alt + .$_相同
!:n 上一条命令的第 n 个参数,索引从 0 开始
!* 上一条命令的所有参数
!:1-$ 上一条命令的所有参数同 !* 相同
!-n:$ 倒数第 n 条命令的最后一个参数
!$:h 上一条命令参数的上一级
!#:1 当前行的第 1 个参数
!!:gs/aa/bb/ 替换上一条命令中所有的 aa 为 bb
^blah 删除上一条命令中的 blah
^blah^foo 将上一条命令中的 blah 替换为 foo

执行之前输入过的命令

经常我们会遇到当输入比较长的命令时执行了时,提示需要 sudo 运行,这个时候下面的技巧就很有用了

sudo !!

只需上面!!两个感叹号,就可代表上一次执行的命令,我们也可以使用sudo !-1代替效果是一样的,!-1代表倒数第一条命令,如果是正数!n那就是执行第 n 条命令,顺序可从history命令获取

打印而不执行

如果我们只想测试可以在以!开头的命令后面加:p,这只会打印输出而不真正执行

ls -al
!!:p         # ls -al

如果想要执行打印出来的命令直接使用Ctrl + p或者向上箭头就可以了

复用历史命令的各参数

有时我们输命令的时候最后一个参数和上一条命令相同,比较常见的是如下情况

mkdir dirA                     # 创建文件夹dirA
cd !$                             # 进入创建的目录
mkdir dirA && cd $_     # 或者使用$_在一行完成

!$表示上一条命令的最后一个参数(但我更喜欢用Alt + .快捷键),如果是倒数第二条那就是!-2:$,序列号写在:前。如果是第 n 个参数看如下例子

tar -zcvf abc abc.tgz    # 想打包abc为abc.tgz但参数顺序写反了,报No such file or directory
tar -zcvf !:3 !:2        # 这就可以了

!:n代表上一条命令的第 n 个参数,注意 n 从 0 开始计数,例如!:0代表上一条 shell 的命令,全部参数用!*或者!:1-$表示

mv a b
!:1-$:p      # 输出`a b`,或者使用`!*:p`结果一样,如果是用`!:0:p`会输出`mv`

上一级目录

当我们将文件a.txt移动并重命名/a/b/c.txt时,我们想进入/a/b目录查看文件,可以如下操作

mv a.txt /a/b/c.txt
cd !$:h

echo a/b/c/d
!-1:$:h:p            #   a/b/c

上面!$:h代表上一条命令最后一个参数的上一级主要是:h这个作用,!-1:$:h:p看起来很复杂其实是一样的代表倒数第一条命令最后一个参数的上一级目录并把它打印了出来

顺便说下cd -cd ~命令,cd -这是快速切换目录,代表马上切到上一次移动过来的目录,没用过的可以试试,使用起来超方便,cd ~是直接回到 home 目录

当前行的参数

如果我们要复用当前输入行的参数咋办呢,可以用!#,比如备份配置文件cp a.conf a.conf.bak可以如下实现

cp a.conf !#:1.bak

注意上面#后面不是注释的意思是一起的!#:1.bak,代表当前行第 1 个参数后面加.bak,其实备份可以不用这么麻烦,可以用更方便的,效果一样

cp a.conf{,.bak}

替换

看下面的例子

echo cat cat cat
!!:s/cat/dog/        # 替换首个出现的 cat 为 dog
!!:gs/cat/dog/       # 把所有 cat 替换为 dog

替换主要使用:s/old/new/,如果要替换所有出现的就是:gs/old/new/

!!:s/cat/dog/上面的替换还可以使用^cat^dog更加简单

使用默认编辑器编辑长命令

在编辑长命令的时候可以按下 ctrl + x, ctrl + e 打开默认的 $EDITOR 编辑命令,编辑好后保存执行

使用 Aliases

alias命令可以轻松自定义属于自己的快捷命令,例如

alias vi="vim"
alias ll="ls -alFtr --color=auto"

上面自定义了vi使用vimll命令是ls命令的加了参数版。

像上面的设置只在当前会话有用,想永久有效可以把命令加入~/.bashrc

自定义快捷键

Bash 支持自定义快捷键,使用bind命令就可以。Bash 快捷键其实是 GNU Readline 快捷键, GNU Readline Library 是一个来接受用户输入的 GNU 软件包。 它是包括 Bash 在内的绝大多数 Shell 的底层库, 甚至 OSX/Windows/Linux 下的绝大多数软件都采用与之兼容快捷键。快捷键的设置其实就是配置 Readline,Readline 中分两种快捷键,一种是 Readline 内部的函数快捷键,另外一种是执行 Shell 命令,设置的时候稍有不同:


bind -l          # 查看Readline中可以使用的内置函数名称

bind -v          # 列出目前的按键配置与其功能

bind -p          # 查看已经绑定的快捷键

# 自定义shell命令
bind -x '"\C-x\C-l":ls -al'   # 绑定自定义执行命令shell命令的快捷键, 绑定后,按[C-x,C-l]就能执行ls -al
bind -X                       # 列出刚-x绑定的命令

# 自定义内置函数快捷键
bind "\C-i":backward-delete-char   # 绑定内置函数backward-delete-char快捷键,现在可以使用"\C-i"删除一个字符
bind -q backward-delete-char       # 查询函数名称对应的快捷键,会发现多了一个刚才我们自定义的"\C-i"

这种设置只是针对当前的会话有效,一旦会话丢失,这样设置的快捷键就会丢失,为了能够让设置的快捷键永久有效,我们就需要将快捷键的配置写入文件。在 Linux 系统中,能永久保存快捷键的地方有两个,全局和用户的配置文件,全局的是/etc/inputrc,而用户的是在用户的根目录下~/.inputrc,全局的会影响所有的用户,而用户根目录下的只会对相应的用户产生影响。

Reference

  1. www.codeceo.com
  2. mp.weixin.qq.com