跳至主要內容

6. 杂项

安图新大约 7 分钟

6. 杂项

原文链接 - Vim 从入门到精通open in new window

附加资源

资源名称简介
七个高效的文本编辑习惯open in new window作者:Bram Moolenaar(即 Vim 的作者)
七个高效的文本编辑习惯 2.0(PDF 版)open in new window同上
IBM DeveloperWorks: 使用脚本编写 Vim 编辑器open in new windowVim 脚本编写五辑
《漫漫 Vim 路》open in new window使用魔抓定制 Vim 插件
《 Vim 实践 (第 2 版)》open in new window轻取 Vim 最佳书籍
Vimcasts.orgopen in new windowVim 录屏演示
为什么是个脚本都用 vi?open in new window常见误区释疑
你不爱 vi,所以你不懂 Vim open in new window简明,扼要,准确的干货

Vim 配置集合

目前,网上有很多流行 Vim 配置集合,对于 Vim 配置集合,个人认为有利有弊。 对于维护的比较好的配置,比如 SpaceVimopen in new window 还是值得尝试的,可以节省很多自行配置的时间。 当然,网上还有很多其他很流行的配置,比如:

常见问题

编辑小文件时很慢

有两个因素对性能影响非常大:

  1. 过于复杂的 正则表达式 。尤其是 Ruby 的语法文件,以前会造成性能下降。(见调试语法文件

  2. 屏幕重绘 。有一些功能会强制重绘所有行。

典型肇事者原因解决方案
:set cursorline会导致所有行重绘:set nocursorline
:set cursorcolumn会导致所有行重绘:set nocursorcolumn
:set relativenumber会导致所有行重绘:set norelativenumber
:set foldmethod=syntax如果语法文件已经很慢了,这只会变得更慢:set foldmethod=manual:set foldmethod=marker 或者使用快速折叠open in new window插件
:set synmaxcol=3000由于内部表示法,Vim 处理比较长的行时会有问题。让它高亮到 3000 列……:set synmaxcol=200
matchparen.vimVim 默认加载的插件,用正则表达式查找配对的括号禁用插件::h matchparen

注意:只有在你真正遇到性能问题的时候才需要做上面的调整。在大多数情况下使用上面提到的选项是完全没有问题的。

编辑大文件的时候很慢

Vim 处理大文件最大的问题就是它会一次性读取整个文件。这么做是由于缓冲区的内部机理导致的(在 vim_devopen in new window 中讨论)。

如果只是想查看的话,tail hugefile | vim - 是一个不错的选择。

如果你能接受没有语法高亮,并且禁用所有插件和设置的话,使用:

$ vim -u NONE -N

这将会使得跳转变快很多,尤其是省去了基于很耗费资源的正则表达式的语法高亮。你还可以告诉 Vim 不要使用交换文件和 viminfo 文件,以避免由于写这些文件而造成的延时:

$ vim -n -u NONE -i NONE -N

简而言之,尽量避免使用 Vim 写过大的文件。

持续粘贴(为什么我每次都要设置 'paste' 模式)

持续粘贴模式让终端模拟器可以区分输入内容与粘贴内容。

你有没有遇到过往 Vim 里粘贴代码之后被搞的一团糟?

这在你使用 cmd+vshirt-insertmiddle-click 等进行粘贴的时候才会发生。 因为那样的话你只是向终端模拟器扔了一大堆的文本。 Vim 并不知道你刚刚是粘贴的文本,它以为你在飞速的输入。 于是它想缩进这些行但是失败了。

这明显不是个问题,如果你用 Vim 的寄存器粘贴,如:"+p ,这时 Vim 就知道了你在粘贴,就不会导致格式错乱了。

使用 :set paste 就可以解决这个问题正常进行粘贴。见 :h 'paste':h 'pastetoggle' 获取更多信息。

如果你受够了每次都要设置 'paste' 的话,看看这个能帮你自动设置的插件:bracketed-pasteopen in new window

点此open in new window查看该作者对于这个插件的更多描述。

Neovim 尝试把这些变得更顺畅,如果终端支持的话,它会自动开启持续粘贴模式,无须再手动进行切换。

在终端中按 ESC 后有延时

如果你经常使用命令行,那么肯定要接触 终端模拟器 ,如 xterm、gnome-terminal、iTerm2 等等(与实际的终端open in new window不同)。

终端模拟器与他们的祖辈一样,使用 转义序列open in new window (也叫 控制序列 )来控制光标移动、改变文本颜色等。转义序列就是以转义字符开头的 ASCII 字符串(用脱字符表示法open in new window表示成 ^[ )。当遇到这样的字符串后,终端模拟器会从终端信息open in new window数据库中查找对应的动作。

为了使用问题更加清晰,我会先来解释一下什么是映射超时。在映射存在歧义的时候就会产生映射超时:

:nnoremap ,a :echo 'foo'<cr>
:nnoremap ,ab :echo 'bar'<cr>

上面的例子中两个映射都能正常工作,但是当输入 ,a 之后,Vim 会延时 1 秒,因为它要确认用户是否还要输入那个 b

转义序列会产生同样的问题:

  • <esc> 作为返回普通模式或取消某个动作的按键而被大量使用
  • 光标键使用转义序列进行的编码
  • Vim 期望 Alt (也叫作 Mate Key )会发送一个正确的 8-bit 编码的高位,但是许多终端模拟器并不支持这个(也可能默认没有启用),而只是发送一个转义序列作为代替。

你可以这样测试上面所提到的事情: vim -u NONE -N 然后输入 i<c-v><left> ,你会看到一个以 ^[ 开头的字符串,表明这是一个转义序列,^[ 就是转义字符。

简而言之,Vim 在区分录入的 <esc> 和转义序列的时候需要一定的时间。

默认情况下,Vim 用 :set timeout timeoutlen=1000,就是说它会用 1 秒的时间来区分有歧义的映射 以及 按键编码。这对于映射来说是一个比较合理的值,但是你可以自行定义按键延时的长短,这是解决该问题最根本的办法:

set timeout           " for mappings
set timeoutlen=1000   " default value
set ttimeout          " for key codes
set ttimeoutlen=10    " unnoticeable small value

:h ttimeout 里你可以找到一个关于这些选项之间关系的小表格。

而如果你在 tmux 中使用 Vim 的话,别忘了把下面的配置加入到你的 ~/.tmux.conf文件中:

set -sg escape-time 0

无法重复函数中执行的搜索

  • 在命令中的搜索(/:substitute 等)内容会改变“上次使用的搜索内容”。(它保存在/寄存器中,用 :echo @/ 可以输出它里面的内容)
  • 简单的文本变化可以通过 . 重做。(它保存在 . 寄存器,用 :echo @. 可以输出它的内容)

而在你在函数中进行这些操作的时候,一切就会变得不同。因此你不能用 N/n 查找某个函数刚刚查找的内容,也不能重做函数中对文本的修改。

帮助文档::h function-search-undo

进阶阅读

参考资料

来源链接:Vim 从入门到精通open in new window