最近 vscode 在技術圈火了一陣子,天天均可以在掘金上看到安利文章和奇葩的插件,什麼"楊超越鼓勵師",還有上班摸魚系列,"看小說插件","看股票插件",讓我愈加以爲 vscode 的功能愈來愈強大,強大到能夠作任何事情,就像操做系統,而這有沒有很像神之編輯器 emacs。最近臺灣 emacs 圈中出了一個叛徒,最後這個維護人叛逃到 vscode 陣營並將這一消息發佈到了臺灣官方 emacs 推特。html
編輯器之爭,在語言還在蓬勃發展的今天仍在持續,Vim 和 Emacs 誰是最好的編輯器,在程序員的圈子裏是一個經久不衰的話題,不論在哪一個地方都能垂手可得的引發一場聖戰。在公司裏使用的開發語言主要是 C++ 和 python,小組同事使用的開發環境也是各類各樣,有 NetBean,vscode,C++ eclipse,pycharm 以及 vim。編輯器或 IDE 始終都只是工具,工具的價值不是看它功能有多強大,有多豐富,要看它能給咱們產生多少價值,因此同個工具的價值沒辦法放在不一樣的人上去比較。個人觀點是若是你在開發過程當中會常用兩到三個語言,開發過程當中習慣的銜接很重要,我會推薦使用 vim;可是IDE是一個通過高度封裝的工具,它對開發流程,開發方式等有必定的假設,因此在不少時候特別是實際項目中,也會爲咱們節約了大量寶貴的時間。python
每種 IDE 都有本身的配置和使用習慣,數量一多,切換來切換去學習成本也很高。除了 vim,平時我也會在 windows 下使用 sublime 看看代碼,由於輕快且在 windows 下能夠快速編輯剪切複製。用過 pycharm 開發過 python,用過一段時間 eclipse 進行 C++ 開發,結合 beyond compare 方便把 windows 下代碼同步到遠程 linux 上,而後再進行 make 編譯,但最後都統一切到了 vim。linux
說說我選擇 vim 做爲主力開發環境的緣由,IDE 不少,學習成本同樣很高,使用 N 種語言就可能會有 N 種 IDE。IDE 有它本身的好處,它已經針對某種語言進行集成優化,用戶須要配置的東西其實不會不少。但其實越高度固化的東西可能越很差用,缺乏必定的靈活性。vim 插件多,支持各類語言,同時也解決了 linux 同步運行問題,著名的插件在 github 和 stackoverflow 都很活躍,一個 vim 解決全部 ide。c++
我使用的 vim 進行 python 和 C++ 進行後臺開發,最主要的功能仍是不能沒有,提示補全,定義跳轉,關鍵詞搜索,語法高亮,語法檢查,縮進摺疊,函數展現大綱,文件模板,目錄樹等等,而個人 vim 如今也能夠方便完成這些功能。git
下面開始說說 2019,我使用的 vim 插件,主要是簡單的介紹,每個我都會簡單介紹插件和使用操做,以及最重要的文檔,由於裏面有更詳細的使用信息。程序員
在 github 上有一個不錯的 vim 學習資源,從最簡單的介紹起:github
Vim 從入門到精通:github.com/wsdjeg/vim-… 笨方法學 vimscript:www.treelib.com/book-detail…正則表達式
另外,不少 vim 插件我還在知乎上關注一些 Vimer,好比:shell
通常都會介紹如何搭建 Vim IDE 和插件。數據庫
另外,我還喜歡在 github 上經過查找 vim 相關的插件,按照 Most Star 降序瀏覽。
個人 .vimrc
參考:github.com/cposture/my…
vim 8 已經支持異步執行功能了,而且在大多數插件中獲得了支持,異步插件管理器,好比 plug.vim,在更新插件不再用等那麼久了,再也不推薦老牌的 vundle。
vim-plug 不只支持異步更新功能,還支持針對文件類型和啓動命令的延遲加載功能,讓 vim 的啓動速度再提升不少。
plug.vim 支持插件延遲加載,不至於不相關的插件一開始都啓動;plug.vim 支持按命令(command)或文件類型(file_type)這兩種配置。
" 在第一次執行 NERDTreeToggle 命令時,NERD tree 插件纔開始加載 Plug 'scrooloose/nerdtree', { 'on': 'NERDTreeToggle' } " on 支持多命令
Plug 'junegunn/vim-github-dashboard', { 'on': ['GHDashboard', 'GHActivity'] }
" 打開 clojure 類型的文件時,vim-fireplace' 纔開始加載 Plug 'tpope/vim-fireplace', { 'for': 'clojure' } " for 支持多文件類型
Plug 'kovisoft/paredit', { 'for': ['clojure', 'scheme'] }
複製代碼
使用 on 延遲加載 YouCompleteMe 方法:
# on 爲空,後面手動加載
Plug '~/YouCompleteMe', {'on': []}
augroup load_ycm
autocmd!
"延遲加載,在 insert 模式手動加載插件 autocmd InsertEnter * call plug#load('YouCompleteMe') | autocmd! load_ycm augroup END 複製代碼
延遲加載不是銀彈,最終要看是否是有這個需求;因此咱們通常在出現啓動比較慢的狀況下才去嘗試使用延遲加載。另外,通常插件的做者都要考慮自己延遲加載功能,而不是依靠等待外部插件去實現延遲加載。
那麼如何啓動速度慢的狀況下分析插件問題呢?
vim 啓動時能夠指定選項,vim --startuptime vim.log -c q
,啓動時把計時信息寫入文件,用於分析載入 .vimrc、插件和打開首個文件的過程當中時哪一步最耗時。
times in msec
clock self+sourced self: sourced script
clock elapsed: other lines
...
003.691 002.008 002.008: sourcing /home/luffichen/.vim/autoload/plug.vim
021.676 000.021 000.021: sourcing /usr/local/share/vim/vim81/filetype.vim
021.869 000.017 000.017: sourcing /usr/local/share/vim/vim81/filetype.vim
...
複製代碼
其中第一列是時間點,第二列和第三列都是時長(區別:第二個是self+sourced,第三個是self),咱們主要關注第三列,腳本自己的執行時間。
由於同一個插件會有多行數據,咱們要手動把同一插件的第三列統計一個總和,這樣很繁瑣,因此 github 上有人寫了一個插件,專門用於分析每一個插件的執行耗時,並輸出直線圖,具體能夠看看:github.com/hyiltiz/vim…
還有其餘分析方法,具體可見: VIM加速:segmentfault.com/a/119000001…
:PlugInstall
,安裝已添加到 .vimrc 的插件:PlugStatus
,查看安裝進度:PlugClean
,刪除不在配置文件裏的插件由於公司的 Linux 開發環境通常沒法鏈接到外網,因此不能直接使用 plug 從 github 上安裝插件,個人方法是:
以 auto-pairs 爲例,
git clone https://github.com/jiangmiao/auto-pairs
rz -bye
,unzip auto-pairs.zip
~/vim-plugin
下,cp -rf auto-pairs ~/vim-plugin/
Plug '~/vim-plugin/auto-pairs'
:PlugInstall
:PlugStatus
這幾個插件完美的解決了 C++ 和 python 的代碼補全和提示,其餘語言能夠參考其餘的介紹。
隨着 vscode lsp 協議的推廣,vim 語法補全也出現了相應的插件,好比 coc.nvim
,主要是異步而且支持不少 vscode 上的語法補全插件,能夠試用一下(ps:公司的系統版本比較老而且網絡不通,因此一直沒去折騰這插件,後面據說出現了一個打包版本,能夠不用安裝,後面有需求能夠試用一下)。
coc.nvim 具體的介紹:zhuanlan.zhihu.com/p/39302327 coc.nvim:github.com/neoclide/co…
目前,C/C++ 的補全的話,請直接使用YouCompleteMe,沒有之一;另外 YCM-Generator 主要用於解決 YouCompleteMe 配置文件生成麻煩問題。
原本最新版本的 YCM 也支持 python 的補全,只要安裝一個 jedi
就能夠了,可是公司開發環境系統版本不是很高,編譯不了最新版本的 YCM,因此安裝一個之後端 jedi 爲補全客戶端的插件 jedi-vim
。
原本還想介紹一下 SuperTab(github.com/ervandew/su…),它實現的功能簡單的說就是用 tab 來調用 vim 的補全功能,這和 linux 操做習慣徹底一致,而且方便而合理,可是 YCM 自己就包含了 SuperTab 的功能,因此再也不多餘的安裝 SuperTab 插件了,以避免衝突。另外 YCM 文檔還說了包含其餘插件的功能,具體以下:
clang_complete
AutoComplPop
Supertab
neocomplcache
複製代碼
最後補充下 omnicomple,有時 YCM 和 jedi-vim 沒辦法在某些狀況下進行補全,好比我常常遇到,我只想補全我以前寫過的一個 word,這個 word 可能只是註釋裏的一個單詞,YCM 沒辦法找出它;這個時候我會使用 omnicomple 命令系列。
:help ins-completion
YCM
YCM 的補全須要對文件進行語法分析,因此須要依賴 .ycm_extra_conf.py
配置文件,生成 .ycm_extra_conf.py
配置文件在 google 上有詳細的介紹,咱們這裏使用 YCM-Generator
插件,能夠對 make 編譯系統生成須要的配置文件。
"=========================================
" YCM-Generator 插件配置
"=========================================
" ctrl-I 自動生成 .ycm_extra_conf.py 文件
noremap <C-I> :YcmGenerateConfig -c g++ -v -x c++ -f -b make .<CR>
複製代碼
上面的配置加到 .vimrc 後,只要在項目根目錄打開後執行快捷鍵 Ctrl - i 後就會自動在當前目錄生成配置文件
ctrl + I
,自動生成 .ycm_extra_conf.py 文件Ctrl + Space
,在任何地方觸發完成建議,即便沒有字符串前綴也是如此。這對於查看哪些頂級函數可供使用頗有用。:YcmRestartServer
,從新啓動:YcmDiags
和 :YcmDebugInfo
,查詢信息:YcmCompleter
命令,配合其餘子選項完成功能,例如,GoToDeclaration
跳轉到聲明處omnicomple
Ctrl-X Ctrl-L
:整行補全Ctrl-X Ctrl-N
:當前文件內關鍵字補全Ctrl-X Ctrl-i
:當前文件及其頭文件內的關鍵字Ctrl-X Ctrl-]
:tags補全Ctrl-X Ctrl-F
:文件名補全Ctrl-X Ctrl-O
:全能 (omni) 補全有了 YCM 補全爲何須要 omni,YCM 沒辦法補全 buffer 內的字符串,這個時候就要用 Ctrl-X Ctrl-N
jedi-vim
leader + d
:定義跳轉,包括語句和 import 模塊leader + n
:查看用法leader + r
:重命名:Pyimport os
:打開模塊 osCtrl + space
:補全vim-polyglot 是一個開箱即用型的語法高亮包,還有對齊功能,支持134 種語言;同時所有語言文件都是針對文件類型進行延遲加載的,不會影響到 vim 的啓動速度。
具體的支持語言能夠參考 github 上的介紹:github.com/sheerun/vim…
幾乎不用加載配置,只須要 vim 打開 syntax 功能。
syntax on
複製代碼
indentLine 是一個顯示豎直對齊線的插件 ,習慣讓代碼整齊,可是插件只支持空格對齊的代碼,因此對於 tab 對齊的不會顯示對齊線;由於不一樣的編輯器對 tab 的展現不太同樣,有的展現 4 個空格,有的展現 8 個;個人習慣是讓 vim 將輸入的 tab 自動轉化爲 4 個空格,這樣的代碼在全部的編輯器的展現都是同樣的。
tab 自動轉化爲 4 個空格:
"將輸入的TAB自動展開成空格。開啓後要輸入TAB,須要Ctrl-V<TAB> set expandtab "使用每層縮進的空格數
set shiftwidth=4
"編輯時一個TAB字符佔多少個空格的位置 set tabstop=4 "方便在開啓了et後使用退格(backspace)鍵,每次退格將刪除X個空格
set softtabstop=4
" 使回格鍵(backspace)正常處理indent(縮進位置), eol(行結束符), start(段首), 很奇怪 Vim 默認居然不容許在這些地方使用 backspace set backspace=indent,eol,start "開啓時,在行首按TAB將加入 shiftwidth 個空格,不然加入 tabstop 個空格
set smarttab
複製代碼
indentLine 配置:
"打開縮進線 let g:indentLine_enabled = 1 let g:indentLine_char='¦' 複製代碼
:IndentLinesToggle
,打開縮進線ale 是一款語法檢查的插件,與syntastic相似,但有一個明顯的優點,一個是語法檢查是異步執行的,所以基本上不會出現卡頓的狀況,但它只支持Vim 8.0以上的版本。
Ale 支持多種語言的各類代碼分析器,就 C/C++ 而言,就支持:gcc, clang, cppcheck 以及 clang-format 等,須要另行安裝並放入 PATH下面,ALE能在你修改了文本後自動調用這些 linter 來分析最新代碼,而後將各類 linter 的結果進行彙總並顯示再界面上。
由於 LSP 協議支持語法檢查,因此 ALE 後面又支持 LSP,又順便支持了 LSP 語法補全功能,致使 ALE 愈來愈龐大,後面我基本只將它做爲語法檢查插件來使用。
ALE 和 clang 的工具集集合起來使用應該很不錯,https://github.com/w0rp/ale/blob/master/doc/ale-c.txt
在這裏有不少關於 clang 的配置選項,支持 compile_commands.json
,免去頭文件查找問題,惋惜公司的系統版本較老。
ale
ale 的配置通常都要指定語言的特定 linter 和 linter 選項;我這裏只配置了 C++,C 和 python 的語法檢查,C++ 和 C 使用 cppcheck,python 使用 pylint;因此這裏須要額外安裝 cppcheck
和 pylint
外部程序。
g:ale_linters
用於指定 linter,同時我配置了只在修改 normal 和離開 insert 時纔會進行語法檢查,避免影響速度。
let g:ale_linters = {
\ 'cpp': ['cppcheck'],
\ 'c': ['cppcheck'],
\ 'python': ['pylint'],
\}
" normal 模式下文字改變運行 linter let g:ale_lint_on_text_changed = 'normal' " 離開 insert 模式的時候運行 linter
let g:ale_lint_on_insert_leave = 1
let g:ale_c_cppcheck_options = '--enable=all'
let g:ale_cpp_cppcheck_options = '--enable=all'
複製代碼
以一小段有代碼展現 cppcheck 和 ale 的語法檢查結果:
int *ptr_list = NULL;
*ptr_list = 1;
複製代碼
最下面的狀態欄和左邊欄都會提示錯誤:Null pointer dereference
,以下:
FlyGrep 是從 SpaceVim(spacevim.org/cn/)中移植出來的實時代碼檢索工具,並且支持正則表達式,配置一個快捷鍵 Ctrl-F 後就和其餘 IDE 的搜索沒有什麼區別了。
FlyGrep 只能搜索當前目錄下的文件,因此若是想搜索整個項目,須要先切換到項目根目錄。
FlyGrep
綁定快捷鍵 Ctrl-F:
"=========================================
" FlyGrep 插件配置
"=========================================
nnoremap <C-F> :FlyGrep<CR>
複製代碼
FlyGrep
Ctrl-F
,在當前目錄下搜索關鍵詞,這裏我通常是在項目根目錄下搜索,因此先移動收到根目錄<Esc>
,退出搜索<Enter>
,進入選中的搜索結果<Tab>
,下一個搜索結果<S-Tab>
,上一個搜索結果<Home>
,第一個開始結果<End>
,最後一個搜索結果vim 自帶
以搜索關鍵詞 "main" 爲例:
:vim /main/ % | copen
:只搜索當前文件
vim /main/ * | copen
:只搜索當前目錄
vim /main/ ../** | copen
:搜索上級目錄下,並遞歸
vim /main path1/** path2/** | copen
:能夠在多個路徑中搜索
說明:
%
表示當前文件copen
用於打開一個窗口,存放搜索結果,方便跳轉C++ 項目常常須要在 header 和對應的 source 文件以前切換;CurtineIncSw 就提供了這樣的功能,不過它的切換是有必定的前提的:
leader-R
:從頭文件和源文件互切換python 的跳轉,我這邊使用的是 jedi-vim 插件;C++ 的跳轉我使用 vim + ctags 工具;標籤的跳轉使用 vim-matchup。
ctags 須要本身安裝。
過去寫幾行代碼又須要運行一下 ctags 來生成索引,每次生成耗費很多時間。
現在 Vim 8 下面自動異步生成 tags 的工具備不少,這裏推薦:vim-gutentags,這個插件主要作兩件事情:
vim-gutentags
" gutentags 搜索工程目錄的標誌,碰到這些文件/目錄名就中止向上一級目錄遞歸 let g:gutentags_project_root = ['.root', '.svn', '.git', '.hg', '.project'] " 所生成的數據文件的名稱
let g:gutentags_ctags_tagfile = '.tags'
" 將自動生成的 tags 文件所有放入 ~/.cache/tags 目錄中,避免污染工程目錄 let s:vim_tags = expand('~/.cache/tags') let g:gutentags_cache_dir = s:vim_tags " 配置 ctags 的參數
let g:gutentags_ctags_extra_args = ['--fields=+niazS', '--extra=+q']
let g:gutentags_ctags_extra_args += ['--c++-kinds=+px']
let g:gutentags_ctags_extra_args += ['--c-kinds=+px']
複製代碼
有了上面的設置,你平時基本感受不到 tags 文件的生成過程了,只要文件修改過,gutentags 都在後臺爲你默默打點是否須要更新數據文件,你根本不用管,還會幫你:setlocal tags+=...
爲當前文件添加上對應的 tags 文件的路勁而不影響其餘文件。得益於 Vim 8 的異步機制,你能夠任意隨時使用 ctags 相關功能,而且數據庫都是最新的。須要注意的是,gutentags 須要靠上面定義的 project_root 裏的標誌,判斷文件所在的工程,若是一個文件沒有託管在 .git/.svn 中,gutentags 找不到工程目錄的話,就不會爲該野文件生成 tags,這也很合理。想要避免的話,你能夠在你的野文件目錄中放一個名字爲 .root 的空白文件,主動告訴 gutentags 這裏就是工程目錄。
ctrl+]
:跳進ctrl+o
:跳回%
:跳轉到下一個標籤vim模板插件 segmentfault.com/a/119000000… Vim爲特定文件載入模板 blog.csdn.net/demorngel/a…
vim-airline 是 powerline 的替代品,而且可以和 tarbar 一塊兒工做。這兩個插件裝完,狀態欄,大綱預覽以及任務欄都齊了。
ctrl+left
,打開文件列表右邊文件ctrl+right
,打開文件列表左邊文件ctrl+n
,打開下一個 tabctrl+p
,打開上一個 tab插件:github.com/tmhedberg/S… 操做:zc關閉摺疊並zo打開摺疊
操做:<<
和 >>
,==命令來縮進當前行,可視化模式選擇多行,使用=命令縮進選中的行 文檔:yyq123.blogspot.com/2010/10/vim…
yum install libX11 libX11-devel libXtst-devel libXtst libXt-devel libXt libSM-devel libSM libXpm libXpm-devel
./configure --prefix=/data/luffichen/bin/vim-8.1 --with-features=huge --with-luajit --enable-luainterp=yes --enable-fail-if-missing --enable-pythoninterp=yes --with-x=yes --enable-gui=auto
grep X11 src/auto/config.h
若是有 #define HAVE_X11 1
#define HAVE_X11_XPM_H 1
#define HAVE_X11_SM_SMLIB_H 1
即表示依賴成功make -j4 && make install
vim --version | grep clipboard
查看是否支持vi /etc/ssh/sshd_config
確認有配置 X11Forwrding yes
,容許SSH的X轉發+y
,便可 安裝luajit :blog.csdn.net/tao_627/art…