vimbook-OPL(5-7)
Contents
vimbook-OPL(5-7)
Chapter 5 Windows
5.1 打开新窗口
分屏的命令有以下命令:
-
:sp
上下分屏,:vs
左右分屏 -
CTRL-W_CTRL-W
在窗口之间切换 -
CTRL-W_h
CTRL-W_j
CTRL-W_k
CTRL-W_l
进行左右上下窗口切换,用:h CTRL-W_h
可以查看对应的帮助文档。 -
:sp file
可以在分屏的同时打开文件,在执行任何打开操作时可以用 +command 打开头执行的一条命令,如:1
:sp +/sprintf three.c
在分屏打开文件后马上执行搜索 sprintf 的命令。
-
CTRL-W_K
将当前窗口放在最顶部的位置,CTRL-W_L
将当前窗口放在最右边的位置,CTRL-W_H
将当前窗口放在最左边的位置,CTRL-W_J
将当前窗口放在最下边的位置;
5.2 控制窗口大小
在sp前面带上数字,会成为新打开的窗口的行数,形如: :10sp alpha.c
将在上下分屏,并且新打开的窗口大小是10行。用 [N]CTRL-W_+
[N]CTRL-W_-
分别增加或减小当前窗口的大小,[N] 指定增加减少的行数,不提供时默认为1行,用 CTRL-W_=
将屏幕对半平分。
5.3 Buffers
A buffer is a copy of a file that you edit along with the setting and marks that go with it.
vim中的一个重要概念就是缓冲,所谓缓冲就是在内存中的文件拷贝附带它们的设置和标记。
在vim中缓冲有三种状态:
- Active 出现在屏幕上
- Hidden 文件没有出现在屏幕上,但是还在内存中,用
:hide
将一个缓存隐藏 - Inactive 文件没有处于编辑状态
用 :buffers
命令查看所有缓冲的信息,信息首列是缓冲序号,第二列是缓冲的状态,第三列是文件名。以下是一些状态字符的含义:
- % 当前窗口的缓冲区
- # 轮换缓冲区(Alternate buffer)
- a 激活缓冲区
- h 隐藏缓冲区
- - 非激活缓冲区
- + 修改过的缓冲区
以下是我在 bx 项目下打开若干文件的输出:
1 h "~/project/bx/src/bx.cpp" line 1
3 h "allocator.h" line 44
5 #h "inline/allocator.inl" line 1
6 %a "os.h" line 23
5.4 选择缓冲
选择一个缓冲,可以用 :buffer number
,number是缓冲的序号,如果你不知道缓冲的需要,那么用 :buffer filename
也能打开对应的缓冲,:[N]bnext
打开下N个缓冲,不提供N默认为下一个 :[N]bprevious
打开上N个缓冲,不提供N时默认为上一个,:[N]bNext
是它的别名,:blast
打开第一个缓冲,:brewind
和 :bfirst
打开第一个缓冲。
可以将分屏命令和缓冲选择命令结合,如 :sbuffer number
:sbuffer filename
:[N]sbnext
:[N]sbprevious
:sblast
:sbfirst
:sbrewind
分别在打开缓冲时进行分屏。
设置optinons :set hidden
,当文件离开屏幕时不变成Inactive,而是变成Hidden
6 Basic Visual Mode
6.1 简介
vim 和 vi 最大区别就在于可视化模式,可视化模式提供了对高亮文本进行操作的便利方式。vim提供三种可视化模式:
v
进入 a character-bycharacter visual mode 字符可视化模式V
进入 linewise visual mode 行可视化模式,只能高亮整个行CTRL-V
进入 Visual Block Mode 块列可视化模式,高亮的是一个矩形块
用 <Esc>
命令退出可视化模式,可以在可视化模式中按别的模式的命令,直接切换各个模式。
NOTE: 前两个模式查看帮助需要在命令前面带上 d_ 比如可视化模式下的 d 命令,用 :h v_d
。块可视化模式查看帮助得在命令前带上前缀 v_b_ 比如块可视化模式下的 r 命令,用 :h v_b_r
6.2 在可视化模式中进行编辑
d
删除高亮的文本D
删除高亮的行y
复制高亮的文本Y
复制高亮的行c
删除高亮文本并进入插入模式C
删除高亮文本所在的整行并进入插入模式J
将高亮的行拼合成一个长的行,中间的所有空白用空格替换gJ
将高亮的行拼合成一个长的行,中间的换行符别删除>
<
将高亮的行向右或向左缩进 “shiftwidth” 的长度=
将高亮的行依据语法格式进行智能缩进CTRL-]
将高亮的文本跳转其定义,此定义的位置需要用 ctags 生成K
对高亮的文本用 man 查询定义,并展示出来
6.3 Visual Block Mode
块列可视模式是非常重要的,能够定义一个高亮一个四边形的文本块,可以做到同时编辑多列,比如做到对多行进行注释。按住 CTRL-V
即进入块列可视模式,其中执行的所有命令将作用于每一行。以下是块列可视模式下可执行的命令(这些命令都有两个特性:1.当某一行太短而不在可视块中时,那一行不受影响;2.如果输入的字符串中有换行符时,只有首行受影响):
I{string}<Esc>
在可视块的左侧的每行插入字符串string,输入时字符串出现在第一行,当按下<Esc>
结束输入时,string神奇的出现在每一行;c
将可视块中的文本删除,并进入插入模式,输入的字符串插入到每一行;C
从可视块的左侧删除到行尾,并进入插入模式,输入的字符串插入到每一行;A
命令在可视块的右边的每行插入字符串。它有点特殊,可以作用于较短的行,短行将用空白符补齐;r{char}
将可视块中的每个字符替换为{char}表示的字符;>
将可视块向右缩进 “shiftwidth” 的长度,起点是可视块的左侧;<
将可视块向左缩进 “shiftwidth” 的长度,影响的仅仅是可视块本身,如果可视块的左侧距离前面的字符不足 shift 长度,那么能缩进多少就缩进多少;
7 Commands for Programmers
这一章主要讲语法高亮、缩进以及如何定位函数、宏、变量的定义,从这一章中可以看出 Vim 的设计初衷应该是为了给 C/C++ 程序员设计的,别的语言支持的就没那么好了。
7.1 语法高亮
命令 :syntax on
启用语法高亮,:h :syntax
查看语法高亮的帮助文档,语法高亮可以标记关键字、字符串和注释等程序文本结构,并对每个标注不同的颜色。颜色在颜色主题 —— 位于 $VIMRUNTIME/colors 目录 —— 配置。Vim 配色方案有两大系列:light 和 dark,用 :set background={light|dark}
进行切换,:set background?
查看当前的配色系。为什么出现这两个呢?原因在于命令行模式下,终端的配色可能是白色的也可能是黑色的,通过设置不同配色方案来适应。如果你使用非标准的文件扩展名,很可能 Vim 不能正常识别,这时候得用 :set filetype={language}
告知 Vim 文件类型。
7.2 缩进命令
程序的结构好坏就是通过缩进来判断的,一个缩进良好的程序对阅读者来说是莫大的帮助,也提升了代码的评分。所有好的开源项目的代码必定有优秀的统一的缩进。[count]<<
命令将光标下 count 行文本向左移动一个 shiftwidth 长度,[count]>>
则向右缩进。:set shiftwidth=4
设置 shiftwidth 长度为 4。<motion
>motion
按照 motion 移动的位置向左/右缩进一个 shiftwidth。motion 可以是 1G
10j
%
等等。
7.3 自动缩进
Vim 中有许多自动缩进的 Options,我主要总结一下自动的缩进:
-
:set cindent
使得文本按照 C 风格程序结构进行自动缩进,必须自动在 if(x) 之后缩进,在 { 之后缩进,在 } 之后回退缩进;:filetype on :autocmd FileType c,cpp :set cindent
以上命令将在识别 C/C++ 文件时自动进行 C 风格缩进,而在其它文件时不这样做,autocmd 是在一些定义好的事件触发之后自动执行的命令;
-
:set smartindent
C 风格的程序缩进是比较复杂的,而智能缩进则比较简单了,遇到 { 就缩进, 遇到 } 就回退缩进,遇到cinwords
Options 中的关键词就增加缩进;这里有必要提一点,Vim 的设计肯定是对 C/C++ 做了特别的支持的,当遇到 # 字符时,那一行不做任何缩进,然后在下一行恢复,这样做是为了给 C 预处理器提供便利; -
:set autoindent
这种模式就很简单了,上面一行是缩进多少,下面一行就缩进一样多。这种模式给 Python、Lua 语言用是十分好的;
7.4 =
命令
=motion
将用 motion 选中的文本用 Vim 内部格式化程序,常用的 motion 就是 %
对一个块进行格式化。这个命令对 C/C++ 语言支持的很好,对 PHP 支持的很差。越发让我感觉 Vim 是专门为 C/C++ 设计的。
7.5 在程序中定位标识(Items)
[CTRL-I
]CTRL-I
在 #include 包含的文件和当前文件中搜索光标下的 word,前面的命令从所有文件的源头搜索第一个,后面的命令从光标之后开始搜索;gd
gD
搜索并把光标定位到变量定义的位置,前者搜索局部变量,后者搜索全局变量。这个命令有时会出错,因为 Vim 不是编译器,没法完全理解程序;[CTRL-D
]CTRL-D
在 #include 包含的文件和当前文件中搜索并把光标定位到宏定义的位置,前者定位从所有文件的源头开始搜索第一个,后者从光标之后开始搜索;[d
]d
与上面的命令一样搜索,在屏幕下方显示第一个而不是跳转,前者从最开始搜索,后者从光标之后搜索;[D
]D
与上面的命令一样搜索,在屏幕下方显示所有定义,前者从最开始搜索,后者从光标之后搜索;
7.6 匹配括号命令
%
是个神奇的命令,跳转到匹配的块的边界,与 d
=
<
>
等命令配合完成复杂的更新(Change)操作。Vim 预定义的可以匹配的标记有 (), {}, [],以及C 语言的块注释 /* */,还有在预处理命令 #if/#ifdef/#ifndef, #else, #endif 之间循环跳转。
那么怎样只选择 {} 的内含大块而不要括号呢?Vim 提供了命令 i{
i}
来选择这个内含大块。组合命令 >i{
将只缩进这个内含大块而括号不动,在可视化模式中可以只选中内含大块。类似的 Vim 提供了 i[
i]
i(
i)
来匹配别的括号中的内含大块。这真是个有用的命令。
7.7 在 man 程序中查找
K
命令将光标下的 word 用 man 程序打开,相当于调用了 man {word}
。用 {num}K
相当于将光标下的 word 调用了 mane {num} {word}
这个 num 就是想要查找的对应的 section 。当写的程序是 Linux 程序,并且调用了 System Call 时,这个命令可以用来查找函数的描述,岂不快哉!
调用的这个外部程序是由 keywordprg
Option 指定的,是可以替换的。
7.8 Tags
Vim 专门为了 C/C++ 语言设计了 Exuberant Ctags(ctags) 程序用来将文本中的各种定义进行索引,然后可以在 Vim 跳转或者查找这些定义,这是比上面讲的命令更加强大的查找功能。在 Vim 中定义用术语 tags 来表示。执行 ctags -R src include
将对 src 和 include 中的文件递归索引,并在当前目录下生成一个 tags 文件。用 :set tags=./tags
设置标签文件。
Vim 对标签提供了丰富的查找命令:
:tag {word}
直接跳转到 word 所在的定义CTRL-]
跳转到光标下 word 所在的定义,并将此标签放到标签栈(Tag Stack)中,用[count]CTRL-T
从标签栈中弹出 count 标签,并回到上 count 个地方,:[count]tag
将当前标签跳转路径上的前 count 个标签重新压入,并跳转到那个标签的位置。 比如跳转的路径 debugPrintf -> debugPrintfVargs -> debugOutput ,当连续两次按 CTRL-T 回到 debugPrintf 时,按:2tag
又会跳到 debugOutput 所在的定义;:tags
显示所有查找过的标签,> 指示的位置是当前所在的标签;:stag {word}
将屏幕分屏并跳转到定义,[count]CTRL-W_]
是CTRL-]
的分屏版本;
还可以进行正则表达式查找呢!:tag /{pattern}
对 pattern 中的模式进行正则匹配并跳转到第一个匹配的定义,正则表达式不要太复杂哦,否则估计没人愿意用。 Vim 提供了如此多的命令,正如 C++ 提供如此的特性一样,“你可以用,但不代表你必须用”。
:tselect {name}
和 :tselect /{pattern}
被设计为显示所有的匹配定义而不是跳转。结果列表中的 Priority 字段是由三个字母组成的,F 代表完全匹配, S 代码时静态(Static)标签否则为全局标签,C 表示标签在当前文件。在列表的最下方有一个提示符,输入序号就可以跳转到对应的定义。g]
对光标下的 word 执行这种查找。:tjump {name}
执行查找并且当只有一个匹配时跳转到这个定义,如果有多个匹配与 :tselect 结果一样。
当查找到不止一个标签时,用 :[count]tnext
下一个标签 :[count]tprevious
上一个标签 :[count]trewind
第一个标签 :[count]tlast
最后一个标签,进行跳转。
为了显示制表符 Tab 和换行符,用 :set list
对于原始的 Vim 将 Tab 显示为 ^I ,在每行的结尾显示 $ ,用 ’listchars’ 改变显示的字符。去文档中查找帮助看下具体如何使用。’expandtab’ 将输入的 Tab 扩展为空格,而用 CTRL-V<Tab>
就不会将 Tab 进行扩展。
7.9 编译程序
Vim 在设计的时候就考虑了通过 make 来编译程序,:make [arguments]
调用当前目录下的 Makefile 以 arguments 为目标和参数,并在屏幕下方回显 Shell 的输出。
当发现错误时,错误显示在 quickfix 中,有以下命令可用:
:[count]cnext
跳转到下 count 个错误;:[count]cprevious
回到上 count 个错误;:crewind
跳到一个错误:clast
调到最后一个错误:cnfile
跳到下一个文件的第一个错误;:cc
回到当前所在的错误:clist [from] [,[to]]
显示错误列表,通过 from 和 to 指定显示的范围:clist!
显示错误列表的所有信息(包括正常信息):cfile [error-file]
将 error-file 中的内容导入到 quickfix 中,如果没有指定将默认使用 ’errorfile’ 选项的值作为文件名,这个多用于帮助其它开发者定位 bug 用,另外一个开发者只需要发送其错误文件过来即可;:cquit
退出错误状态。
选项 ‘makeprg’ 指定默认的 make 程序;
7.10 Grep 查找
:grep [arguments]
调用外部的 grep 程序,arguments 与在 Shell 中调用 grep 是一样的。结果将显示在 Vim 的 quickfix 中,可用命令与 :make
一样。
7.11 modeline
每个文件可以包含一个模式行,模式行必须在文件的第一行或者最后一行,格式固定用对应语言的注释语法,如 C 的
/* vim: set ai tw=75: */
vim: set
之前必须有一个空格,命令必须以 :
结束,中间用空格隔开的是个 set 的 Options。
Author zoro.wang
LastMod 2017-11-18