Skip to content

Commit

Permalink
Add an article
Browse files Browse the repository at this point in the history
  • Loading branch information
liuzhaoze committed Oct 6, 2024
1 parent 2113179 commit dc33591
Showing 1 changed file with 324 additions and 0 deletions.
324 changes: 324 additions & 0 deletions _posts/2024-10-04-vim命令助记.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,324 @@
---
title: vim 命令助记
date: 2024-10-04 13:14:25 +0800
categories: [Linux]
tags: [linux, vim] # TAG names should always be lowercase
---

## 模式、保存和退出

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>i</kbd>|进入编辑模式|insert (在光标前方**插入**)|
|<kbd>ESC</kbd> / <kbd>Ctrl</kbd> + <kbd>C</kbd>|进入普通模式|推荐使用 <kbd>Ctrl</kbd> + <kbd>C</kbd>|
|<kbd>:</kbd>|进入命令行模式||
|`:q`|仅退出|quit|
|`:q!`|不保存退出|! (强制)|
|`:w`|仅保存|write|
|`:wq`|保存并退出||

## 光标移动和编辑

### 单行移动光标和字符输入

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>j</kbd>|下移光标||
|<kbd>k</kbd>|上移光标||
|<kbd>h</kbd>|左移光标||
|<kbd>l</kbd>|右移光标||
|<kbd>i</kbd>|在光标前方编辑|insert (在光标前方**插入**)|
|<kbd>a</kbd>|在光标后方编辑|append (在光标后方**追加**)|
|<kbd>I</kbd>|在行首编辑||
|<kbd>A</kbd>|在行尾编辑||
|<kbd>o</kbd>|在下方插入新行编辑|open a new line|
|<kbd>O</kbd>|在上方插入新行编辑||
|<kbd>r{char}</kbd>|替换光标所在的字符为 `{char}`|replace|

> 使用 <kbd>{number}i/I/a/A/o/O</kbd> `{content}` <kbd>ESC</kbd> 可以重复输入 `{content}` `{number}` 次。
> 例:<kbd>3o</kbd> `Hello World!` <kbd>ESC</kbd> 可以在当前行下方插入三行 `Hello World!`
> 例:<kbd>3A</kbd> `Hello World!` <kbd>ESC</kbd> 可以在当前行尾追加三次 `Hello World!`
### 跳跃移动光标

#### 行间跳跃

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>G</kbd>|光标移动到最后一****行首|**go** to the end of file|
|<kbd>gg</kbd>|光标移动到第一****行首|**go** to the beginning of file|
|<kbd>{number}j</kbd>|光标向下移动 `{number}` ****|编辑器启用 relative line number|
|<kbd>{number}k</kbd>|光标向上移动 `{number}` ****|编辑器启用 relative line number|

#### 行内跳跃

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>0</kbd>|光标移动到****||
|<kbd>$</kbd>|光标移动到****||
|<kbd>^</kbd>|光标移动到****首第一个非空字符||
|<kbd>g_</kbd>|光标移动到****尾最后一个非空字符||

#### 按单词跳跃

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>w</kbd>|光标移动到下一个**单词**首部|word|
|<kbd>e</kbd>|光标移动到下一个**单词**尾部|end of the word|
|<kbd>b</kbd>|光标移动到上一个**单词**首部|back|
|<kbd>ge</kbd>|光标移动到上一个**单词**尾部||
|<kbd>*</kbd>|查找下一个与光标所在单词相同的单词||
|<kbd>#</kbd>|查找上一个与光标所在单词相同的单词||
|`/{pattern}` <kbd>Enter</kbd>|光标移动到下一个匹配的字符串||
|`?{pattern}` <kbd>Enter</kbd>|光标移动到上一个匹配的字符串||
|<kbd>n</kbd>|重复上一次的 <kbd>*</kbd>、<kbd>#</kbd>、`/``?` 命令||
|<kbd>N</kbd>|反向重复上一次的 <kbd>*</kbd>、<kbd>#</kbd>、`/``?` 命令||

#### 按字符跳跃

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>f{char}</kbd>|光标移动到下一个匹配的字符|find|
|<kbd>F{char}</kbd>|光标移动到上一个匹配的字符||
|<kbd>t{char}</kbd>|光标移动到下一个匹配的字符前一个位置|until|
|<kbd>T{char}</kbd>|光标移动到上一个匹配的字符后一个位置||
|<kbd>;</kbd>|重复上一次的 `f``F``t``T` 命令||
|<kbd>,</kbd>|反向重复上一次的 `f``F``t``T` 命令||

> <kbd>t{char}</kbd> 通常作为 `{motion}`[删除命令](#删除字符串) <kbd>d</kbd> <kbd>c</kbd> 或[复制命令](#复制和粘贴) <kbd>y</kbd> 配合使用,用于处理括号或引号内的内容 `{char} = ) 或 ] 或 } 或 " 或 '`
#### 按括号跳跃

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>%</kbd>|光标移动到匹配的括号处|如果光标在括号外,先移动到右括号,再按一次移动到左括号;<br>如果光标在括号内,先移动到左括号,再按一次移动到右括号。|

#### 按段落跳跃

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>{</kbd>|光标移动到上一个**段落**||
|<kbd>}</kbd>|光标移动到下一个**段落**||

> 段落使用空行分隔。
#### 按页跳跃

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>Ctrl</kbd> + <kbd>d</kbd>|光标向下移动半页|down|
|<kbd>Ctrl</kbd> + <kbd>u</kbd>|光标向上移动半页|up|

#### 按句子跳跃

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>(</kbd>|光标移动到上一个**句子**首部||
|<kbd>)</kbd>|光标移动到下一个**句子**首部||

### 删除

#### 删除字符

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>x</kbd>|删除光标所在的字符||
|<kbd>X</kbd>|删除光标所在的字符的前一个字符||
|<kbd>s</kbd>|删除光标所在的字符并进入编辑模式|substitute|

#### 删除字符串

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>dd</kbd>|删除光标所在的行|delete|
|<kbd>dw</kbd>|删除光标处到下一个单词之前的内容||
|<kbd>cc</kbd>|删除光标所在的行并进入编辑模式|change|
|<kbd>cw</kbd>|删除光标处到下一个单词之前的内容并进入编辑模式||
|<kbd>D</kbd>|删除光标所在位置到行尾的内容||
|<kbd>{number}D</kbd>|删除光标所在位置到第 `{number} - 1` 行行尾的内容||
|<kbd>C</kbd>|删除光标所在位置到行尾的内容并进入编辑模式||
|<kbd>{number}C</kbd>|删除光标所在位置到第 `{number} - 1` 行行尾的内容并进入编辑模式||

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>di{</kbd> 或 <kbd>di}</kbd>|删除大括号内的内容|delete inside {} (光标需位于大括号之间)|
|<kbd>di[</kbd> 或 <kbd>di]</kbd>|删除中括号内的内容|delete inside [] (光标需位于中括号之间)|
|<kbd>di(</kbd> 或 <kbd>di)</kbd>|删除小括号内的内容|delete inside () (光标需位于小括号之间)|
|<kbd>ci{</kbd> 或 <kbd>ci}</kbd>|删除大括号内的内容并进入编辑模式|change inside {} (光标需位于大括号之间)|
|<kbd>ci[</kbd> 或 <kbd>ci]</kbd>|删除中括号内的内容并进入编辑模式|change inside [] (光标需位于中括号之间)|
|<kbd>ci(</kbd> 或 <kbd>ci)</kbd>|删除小括号内的内容并进入编辑模式|change inside () (光标需位于小括号之间)|

引号 `"``'``` ` `` 同样可以使用上述命令。

> 其他删除命令 <kbd>d{motion}</kbd>:<kbd>de</kbd> <kbd>dE</kbd> <kbd>dW</kbd> <kbd>db</kbd> <kbd>dB</kbd> <kbd>dj</kbd> <kbd>dk</kbd> <kbd>d{number}l</kbd> <kbd>d{number}h</kbd> <kbd>d{number}j</kbd> <kbd>d{number}k</kbd> <kbd>d{number}t{char}</kbd>
> 删除范围与光标移动 `{motion}` 后的位置有关。
### 复制和粘贴

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>yy</kbd>|复制当前行|yank|
|<kbd>yw</kbd>|复制光标处到下一个单词之前的内容||
|<kbd>p</kbd>|粘贴到光标后方(复制一个词)或下方(复制一整行)|paste|
|<kbd>{number}p</kbd>|粘贴 `{number}`||
|<kbd>P</kbd>|粘贴到光标前方(复制一个词)或上方(复制一整行)||

> 除了复制命令 <kbd>y</kbd> 以外,使用[删除命令](#删除) <kbd>x</kbd> <kbd>s</kbd> <kbd>d</kbd> <kbd>c</kbd> 删除的内容也会被保存到剪贴板中,可以使用 <kbd>p</kbd> 粘贴。
### 重复操作命令、撤销和重做

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>.</kbd>|重复上一次操作||
|<kbd>u</kbd>|撤销上一次操作|undo|
|<kbd>Ctrl</kbd> + <kbd>r</kbd>|重做之前被撤销的操作|redo|

> <kbd>u</kbd> 和 <kbd>Ctrl</kbd> + <kbd>r</kbd> 是一对逆操作;<kbd>.</kbd> 是单独的一种操作,用于重复上一次操作。
### 缩进

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>&gt;&gt;</kbd>|向右缩进当前行||
|<kbd>&lt;&lt;</kbd>|向左缩进当前行||
|<kbd>&gt;{number}j</kbd> / <kbd>&gt;{number}k</kbd>|向右缩进当前行以及下/上 `{number}`||
|<kbd>&lt;{number}j</kbd> / <kbd>&lt;{number}k</kbd>|向左缩进当前行以及下/上 `{number}`||

> 使用 <kbd>.</kbd> 可以重复上一次的缩进操作。
### 大小写

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>~</kbd>|切换光标所在字符的大小写||

## Visual Mode

### 进入 Visual Mode

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>v</kbd>|类似于鼠标拖动的选中模式||
|<kbd>V</kbd>|整行选中模式||
|<kbd>Ctrl</kbd> + <kbd>v</kbd>|块选中模式||

### 在 Visual Mode 下的操作

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>h</kbd> <kbd>j</kbd> <kbd>k</kbd> <kbd>l</kbd>|移动光标,选中需要操作的区域||
|<kbd>d</kbd>|删除选中区域|delete|
|<kbd>D</kbd>|删除选中区域所在的整行||
|<kbd>y</kbd>|复制选中区域|yank|
|<kbd>Y</kbd>|复制选中区域所在的整行||
|<kbd>c</kbd>|删除选中区域并进入编辑模式|change|
|<kbd>C</kbd>|删除选中区域到行尾的内容并进入编辑模式||

## 视图

### 滚动页面

|Command|Description|Note|
|:-:|:-:|:-:|
|<kbd>zz</kbd>|将光标所在行置于屏幕中央||
|<kbd>zt</kbd>|将光标所在行置于屏幕顶部||
|<kbd>zb</kbd>|将光标所在行置于屏幕底部||

## 命令行命令

### 替换

|Command|Description|Note|
|:-:|:-:|:-:|
|`:%s/{old}/{new}/g` <kbd>Enter</kbd>|将所有匹配的 `{old}` 替换为 `{new}`|**s**ubstitute **g**lobal|

## 剪贴板 (寄存器)

[复制和粘贴](#复制和粘贴)部分提到了通过[复制命令](#复制和粘贴) <kbd>y</kbd> 和[删除命令](#删除) <kbd>x</kbd> <kbd>s</kbd> <kbd>d</kbd> <kbd>c</kbd> 复制或删除的内容会保存到剪贴板中。

实际上,vim 中的剪贴板被称为寄存器,并且存在多个。寄存器可以通过 `"{register}` 命令访存,其中 `{register}` 可以是数字 (`0` ~ `9`)、小写字母 (`a` ~ `z`)、大写字母 (`A` ~ `Z`) 或特殊字符 (`"``-``:``.``%``#``=``*``+``~``_``/`)。

使用 `:reg` 命令可以查看当前所有寄存器的内容。

在复制命令和删除命令前输入 `"{register}` 可以将内容保存到指定的寄存器中,例如:<kbd>"ayy</kbd> 可以将当前行复制到寄存器 `a` 中;<kbd>"bdd</kbd> 可以将当前行删除并保存到寄存器 `b` 中。

在粘贴命令前输入 `"{register}` 可以从指定的寄存器中粘贴内容,例如:<kbd>"ap</kbd> 或 <kbd>"bP</kbd> 。

下面使用中文**简单**介绍 vim 中总计 10 种寄存器。对于**更严谨**的说明,请使用 `:help registers` 命令查看,或阅读 [vim 寄存器文档](https://vimhelp.org/change.txt.html#registers)

### vim 中的 10 种寄存器

#### 1 匿名寄存器 `""`

匿名寄存器 `""` 会存储最近一次复制或删除命令 <kbd>y</kbd> <kbd>x</kbd> <kbd>s</kbd> <kbd>d</kbd> <kbd>c</kbd> 涉及到的内容,无论该操作是否指定了寄存器。当粘贴操作没有指定寄存器时,会使用匿名寄存器中的内容。

实际上,匿名寄存器的行为应该是**指向最后使用的寄存器**。因为当使用大写字母的寄存器名称进行追加操作时,匿名寄存器会包含与命名寄存器相同的文本。

有一个例外是黑洞寄存器 `"_`,它会丢弃任何复制或删除的内容,不会保存到任何寄存器中。因此匿名寄存器永远不会指向黑洞寄存器。

#### 2 数字寄存器 `"0` ~ `"9`

数字寄存器 `"0` 会保存最近一次**复制** <kbd>y</kbd> 的内容,除非在复制命令前指定了其他寄存器。

数字寄存器 `"1` ~ `"9` 会保存最近 9 次**删除** <kbd>d</kbd> <kbd>c</kbd> 一行及以上的内容。当删除的内容小于一行时,不会保存到数字寄存器中,而是保存到小删除寄存器 `"-` 中。

#### 3 小删除寄存器 `"-`

小删除寄存器 `"-` 会保存最近一次**删除** <kbd>x</kbd> <kbd>s</kbd> <kbd>d</kbd> <kbd>c</kbd> 小于一行的内容,除非在删除命令前指定了其他寄存器。

#### 4 命名寄存器 `"a` ~ `"z``"A` ~ `"Z`

26 个命名寄存器只有在复制和删除命令 <kbd>y</kbd> <kbd>x</kbd> <kbd>s</kbd> <kbd>d</kbd> <kbd>c</kbd> 前指定了寄存器时才会保存内容。

使用小写字母指定寄存器 `"a` ~ `"z` 时,会**覆盖**寄存器中的内容;使用大写字母指定寄存器 `"A` ~ `"Z` 时,会将内容**追加**到寄存器已有内容的后面。

#### 5 只读寄存器 `":``".``"%`

`":` 寄存器会保存最近一次在**命令模式**下执行的命令,可以使用 `@:` 重复执行上一次命令。

`".` 寄存器会保存最近一次在**编辑模式**下输入的文本。

`"%` 寄存器会保存当前工作目录到该文件的相对路径。

#### 6 交替文件寄存器 `"#`

#### 7 表达式寄存器 `"=`

#### 8 选择和拖拽寄存器 `"*``"+``"~`

#### 9 黑洞寄存器 `"_`

黑洞寄存器 `"_` 用来实现在不影响其他寄存器的情况下使用删除命令 <kbd>x</kbd> <kbd>s</kbd> <kbd>d</kbd> <kbd>c</kbd> 删除内容。

#### 10 搜索寄存器 `"/`

搜索寄存器 `"/` 会保存最近一次使用 `/``?` 命令搜索的内容。

可以使用 `:let @/ = {content}` 命令设置搜索寄存器的内容。

## 标记 (Mark)

vim 可以在文件中设置标记,用于快速跳转到指定位置。

### 设置标记

使用 <kbd>m{char}</kbd> 命令设置标记,其中 `{char}` 可以是小写字母 (`a` ~ `z`) 或大写字母 (`A` ~ `Z`)。

小写字母标记仅用于当前文件内跳转,大写字母标记可以用于跨文件跳转。

### 查看标记

使用 `:marks` 命令可以查看所有标记。

### 跳转标记

使用 <kbd>`{char}</kbd> 或 <kbd>'{char}</kbd> 命令可以跳转到指定标记处。

- <kbd>`{char}</kbd> 跳转到标记的具体位置
- <kbd>'{char}</kbd> 跳转到标记所在行的第一个非空字符

### 删除标记

使用 `:delm {char1} {char2} ...` 命令可以删除指定的标记。

使用 `:delm!` 命令可以删除所有标记。

0 comments on commit dc33591

Please sign in to comment.