更多參見:
http://www.kuqin.com/developtool/20080601/9136.html
第一節:
本節所用命令的協助入口:
:help ‘tags’
:help :tag
:help :tags
:help CTRL-]
:help CTRL-T
:help vimgrep
:help cw
:help pattern
儘管相關的文章已經很多了,但tag檔案實在是太有用了,所以還是囉嗦一次。
Tag檔案(標籤檔案)無疑是開發人員的利器之一,有了tag檔案的協助,你可以在VIM查看函數調用關係,類、結構、宏等的定義,可以在任意標籤
中跳轉、返回……相信使用過Source Insight的人對這些功能並不陌生,而在VIM中,此功能的實現依賴於tag檔案。
對於程式來說,Tag檔案中儲存了諸如函數、類、結構、宏等的名字,它們所處的檔案,以及如何通過Ex命令跳轉到這些標籤。它是一個純文字檔案,因此你可以手工的編輯它,也可以使用指令碼對其進行操作。
通常我們使用名為ctags的程式來產生這樣的tag檔案。VIM能直接使用ctags程式所產生的tag檔案。在UNIX系統下的ctags功能
比較少,所以一般我們使用Exuberant
Ctags(在大多數Linux系統上,它是預設的ctags程式),它能夠支援多達33種程式語言,足以滿足我們開發的需要了。如果你的系統上未安裝此
程式,請到http://ctags.sourceforge.net下載。
EMACS則使用etags來產生tag檔案,如果希望VIM也能支援etags的tag檔案格式,需要在編譯VIM時加入” +emacs_tags”選項。
Tag檔案需要遵循一定的格式,由Exuberant Ctags產生的tag檔案,預設是如下格式:
{tagname} {TAB} {tagfile} {TAB} {tagaddress} {term} {field} ..
{tagname} 標識符名字,例如函數名、類名、結構名、宏等。不能包含定位字元。
{tagfile} 包含 {tagname} 的檔案。它不能包含定位字元。
{tagaddress} 可以定位到 {tagname}游標位置的 Ex 命令。
{term} 設為“;"”。這是為了相容Vi編輯器,使Vi忽略後面的{field}欄位。
{field} .. 此欄位可選,通常用於表示此{tagname}的類型是函數、類、宏或是其它。
在{tagname}、{tagfile}和{tagaddress}之間,採用定位字元(TAB符,即C語言中的”/t”)分隔,也就是說{tagname}、{tagfile}中不能包含定位字元。
Tag檔案的開頭可以包含以“!_TAG_”開頭的行,用來在tag檔案中加入其它資訊。VIM能夠識別兩種這樣的標記,經常用到的是“_TAG_FILE_SORTED”標記,例如:
!_TAG_FILE_SORTED<Tab>1<Tab>{anything}
上面這個標記說明tag檔案是經過排序的,並且排序時區分了大小寫,對排序的tag,VIM會使用二分法來進行尋找,大大加快了尋找速度;如果值為0,則表示tag檔案未經排序;如果值為2,則表示tag檔案是忽略大小寫排序的。
之所以在這裡介紹tag檔案的格式,是因為我們在後面提到的lookupfile外掛程式中,會自己產生tag檔案。
雖然ctags有為數眾多的選項,但通常我們所使用的非常簡單。還是以VIM 7.0的代碼為例,我們執行:
cd ~/src/vim70
ctags –R src
上面這條命令會在~/src/vim70/目錄下產生一個名為tags的檔案,這個檔案中包含~/src/vim70/src/目錄下所有.c、.h檔案中的標籤。它一個文字檔,你可以用VIM開啟它看一下。此檔案預設按區分字母大小寫排序,所以直接可以被VIM使用。
現在我們進入VIM,執行下面的命令:
:cd ~/src/vim70 "切換目前的目錄為~/src/vim70
:set tags=tags "設定tags選項為目前的目錄下的tags檔案
現在,我們設定好了tags選項,接下來我們使用它:
:tag VimMain
你會看到VIM開啟了src/main.c檔案,並把游標定位到第167行VimMain上。
我們知道,一般主程式的函數名為main,如果你嘗試下面的命令:
:tag main
# pri kind tag file
1 F f main src/xxd/xxd.c
main(argc, argv)
2 FS d main src/if_python.c
46
Choice number (<Enter> cancels):
這裡並沒有src/main.c檔案,怎麼回事呢?這是因為ctags並不是編譯器,它在處理編譯預先處理指令受到局限,因此並沒有產生src/main.c中main()函數的標籤。你可以在產生tag檔案時給ctags指定參數來解決這個問題。
或者你可以用”:grep”或”:vimgrep”來尋找main(這已經超出本文的範圍了,因此只給出例子,在後續的文章再做講解):
:cd ~/src/vim70
:vimgrep //<main/>/ src/*.c
:cw
這時下面的視窗將顯示出來,在quickfix視窗中找到我們想跳轉的位置(本例中是src/main.c),按斷行符號,就可以跳到對應的位置了。
如果你只記得部分的標籤名,那麼可以使用“tag”命令的搜尋模式,你可以輸入一個VIMRegex來表示你所尋找的名字,如:
:tag //C/</k/+ain/>
# pri kind tag file
1 F f VimMain src/main.c
VimMain
2 F d bindtextdomain src/vim.h
483
3 F d bindtextdomain src/vim.h
502
4 F d bindtextdomain src/vim.h
504
5 F f main src/xxd/xxd.c
main(argc, argv)
6 F d textdomain src/vim.h
488
7 F d textdomain src/vim.h
510
8 F d textdomain src/vim.h
512
9 FS d bindtextdomain src/gui_gtk.c
54
10 FS d bindtextdomain src/gui_gtk_x11.c
37
11 FS f cmdsrv_main src/main.c
cmdsrv_main(argc, argv, serverName_arg, serverStr)
12 FS d main src/if_python.c
46
13 FS d textdomain src/gui_gtk.c
51
14 FS d textdomain src/gui_gtk_x11.c
34
Choice number (<Enter> cancels):
這表示我想尋找一個以一個或多個keyword開始的標籤,此標籤以ain做為結尾,在尋找時區分大小寫。要讀懂這個Regex,請“:help pattern”。
VIM會儲存一個跳轉的標籤棧,以允許你在跳轉到一個標籤後,再跳回來,可以使用“:tags”命令尋找你處於標籤棧的哪個位置。
我們經常用到的tag跳轉命令見下(一般只需要知道CTRL-]和CTRL-T就可以了):
:tag {ident} "跳轉到指定的標籤
:tags "顯示標籤棧
CTRL-] "跳轉到當前游標下的標籤
CTRL-T "跳到標籤棧中較早的標籤
如果想瞭解更多命令,可以“:help 29.1”(強烈建議程式員完整的閱讀usr_29.txt和usr_30.txt)。
如果想更深入瞭解tag命令和相關知識,可以“:help tagsrch”。
我之前寫的一篇關於ctags和cscope的文章,參見:Vim + Cscope/Ctags
第二節:
本節所用命令的協助入口:
:help helptags
:help taglist.txt
上篇文章介紹了在VIM中如何使用tag檔案,本文主要介紹如何使用taglist外掛程式。
想必用過Source
Insight的人都記得這樣一個功能:SI能夠把當前檔案中的宏、全域變數、函數等tag顯示在Symbol視窗,用滑鼠點上述tag,就跳到該tag
定義的位置;可以按字母序、該tag所屬的類或scope,以及該tag在檔案中出現的位置進行排序;如果切換到另外一個檔案,Symbol視窗更新顯示
這個檔案中的tag。
在VIM中的taglist外掛程式所實現的就是上述類似的功能,有些功能比SI弱,有些功能比SI更強。而且,taglist外掛程式仍在不斷完善中!
要使用taglist外掛程式,必須滿足:
1. 開啟VIM的檔案類型自動檢測功能;
2. 系統中裝了Exuberant ctags工具,並且taglist能夠找到此工具(因為taglist需要調用它來產生tag檔案);
3. 你的VIM支援system()調用;
在
本系列第3篇文章(vimrc初步)中,我們使用了VIM內建的樣本vimrc,這個vimrc中已經開啟了檔案類型檢測功能;在上篇文章中,我們也已用
到了Exuberant ctags;system()調用在一般的VIM版本都會支援(只有suse
Linux發行版中出於安全考慮,關閉了此功能),所以我們已經滿足了這三個條件。
現在我們到http://www.vim.org/scripts/script.php?script_id=273下載最新版本的taglist plugin,目前版本是4.3。
下載後,把該檔案在~/.vim/目錄中解壓縮,這會在你的~/.vim/plugin和~/.vim/doc目錄中各放入一個檔案:
plugin/taglist.vim – taglist外掛程式
doc/taglist.txt - taglist協助檔案
註:windows使用者需要把這個外掛程式解壓在你的$VIM/vimfiles或$HOME/vimfiles目錄。
使用下面的命令產生協助標籤(下面的操作在VIM中進行):
:helptags ~/.vim/doc
產生協助標籤後,你就可以用下面的命令查看taglist的協助了:
:help taglist.txt
Taglist提供了相當多的功能,我的vimrc中這樣配置:
""""""""""""""""""""""""""""""
" Tag list (ctags)
""""""""""""""""""""""""""""""
if MySys() == "windows" "設定windows系統中ctags程式的位置
let Tlist_Ctags_Cmd = 'ctags'
elseif MySys() == "linux" "設定linux系統中ctags程式的位置
let Tlist_Ctags_Cmd = '/usr/bin/ctags'
endif
let Tlist_Show_One_File = 1 "不同時顯示多個檔案的tag,只顯示當前檔案的
let Tlist_Exit_OnlyWindow = 1 "如果taglist視窗是最後一個視窗,則退出vim
let Tlist_Use_Right_Window = 1 "在右側視窗中顯示taglist視窗
這樣配置後,當你輸入“:TlistOpen”時,顯示如下視窗:
在螢幕右側出現的就是taglist視窗,你從中可以看到在main.c檔案中定義的所有tag:宏、定義、變數、函數等;你也可以雙擊某
個tag,跳到該tag定義的位置;你還可以把某一類的tag摺疊起來(使用了VIM的折行功能),方便查看,就像圖中macro和variable那
樣。更多的功能,請查看taglist的協助頁,本文也會介紹一些常用功能。
下面介紹常用的taglist配置選項,你可以根據自己的習慣進行配置:
- Tlist_Ctags_Cmd選項用於指定你的Exuberant ctags程式的位置,如果它沒在你PATH變數所定義的路徑中,需要使用此選項設定一下;
- 如果你不想同時顯示多個檔案中的tag,設定Tlist_Show_One_File為1。預設為顯示多個檔案中的tag;
-
設定Tlist_Sort_Type為”name”可以使taglist以tag名字進行排序,預設是按tag在檔案中出現的順序進行排序。按tag出現
的範圍(即所屬的namespace或class)排序,已經加入taglist的TODO List,但尚未支援;
- 如果你在想taglist視窗是最後一個視窗時退出VIM,設定Tlist_Exit_OnlyWindow為1;
- 如果你想taglist視窗出現在右側,設定Tlist_Use_Right_Window為1。預設顯示在左側。
- 在gvim中,如果你想顯示taglist菜單,設定Tlist_Show_Menu為1。你可以使用Tlist_Max_Submenu_Items和Tlist_Max_Tag_Length來控制功能表條目數和所顯示tag名字的長度;
- 預設情況下,在雙擊一個tag時,才會跳到該tag定義的位置,如果你想單擊tag就跳轉,設定Tlist_Use_SingleClick為1;
- 如果你想在啟動VIM後,自動開啟taglist視窗,設定Tlist_Auto_Open為1;
- 如果你希望在選擇了tag後自動關閉taglist視窗,設定Tlist_Close_On_Select為1;
- 當同時顯示多個檔案中的tag時,設定Tlist_File_Fold_Auto_Close為1,可使taglist只顯示當前檔案tag,其它檔案的tag都被摺疊起來。
- 在使用:TlistToggle開啟taglist視窗時,如果希望輸入焦點在taglist視窗中,設定Tlist_GainFocus_On_ToggleOpen為1;
- 如果希望taglist始終解析檔案中的tag,不管taglist視窗有沒有開啟,設定Tlist_Process_File_Always為1;
- Tlist_WinHeight和Tlist_WinWidth可以設定taglist視窗的高度和寬度。Tlist_Use_Horiz_Window為1設定taglist視窗橫向顯示;
在taglist視窗中,可以使用下面的快速鍵:
<CR> 跳到游標下tag所定義的位置,用滑鼠雙擊此tag功能也一樣
o 在一個新開啟的視窗中顯示光線標下tag
<Space> 顯示光線標下tag的原型定義
u 更新taglist視窗中的tag
s 更改排序方式,在按名字排序和按出現順序排序間切換
x taglist視窗放大和縮小,方便查看較長的tag
+ 開啟一個摺疊,同zo
- 將tag摺疊起來,同zc
* 開啟所有的摺疊,同zR
= 將所有tag摺疊起來,同zM
[[ 跳到前一個檔案
]] 跳到後一個檔案
q 關閉taglist視窗
<F1> 顯示協助
可以用“:TlistOpen”開啟taglist視窗,用“:TlistClose”關閉taglist視窗。或者使用“:TlistToggle”在開啟和關閉間切換。在我的vimrc中定義了下面的映射,使用“,tl”鍵就可以開啟/關閉taglist視窗:
map <silent> <leader>tl :TlistToogle<cr>
Taglist外掛程式還提供了很多Ex命令,你甚至可以用這些命令建立一個taglist的會話,然後在下次進入VIM時載入此會話。
來自:http://blog.csdn.net/easwy/archive/2007/03/01/1518468.aspx