Linux 基礎學習篇 - Fedora Core 4

第十章、 vi 文書處理器 - for Fedora Core 4

利用 vi 這個文書處理器喔!

最近更新時間: 2005/08/01

本文資料主要針對 Fedora Core 4 的系統進行說明, Fedora Core 1 主要是由 Red Hat Linux 9 改版而來, 這個 Red Hat Linux 9 並不是當前大家聽到的 RHEL 喔!那是在 RHEL 出現之前的產品,基本上是在 2003 年以前的作品了!Fedora Core 4 則是在 2005 年 6 月份釋出,使用的核心是 2.6.11 版,當時是很紅的一個作品!只是生命週期太短,所以用這個 Fedora 系列來介紹 Server, 當時的決定確實有點莫名其妙了...

建議您前往本站查詢最新版本的 Linux distribution 文章來閱讀,比較不會浪費時間。那為何還需要編輯 Fedora Core 4 的資料呢? 鳥哥只想要做個自己曾經撰寫過的文件內容保存而已囉! ^_^!最新文章請前往鳥站首頁查閱囉!

每個系統管理員都應該至少要學會一種文字介面的文書處理器,以方便系統日常的管理行為。 在 Linux 上頭的文書處理軟體非常的多,不過,鳥哥還是建議使用 vi 這個正規的文書處理器。 這是因為 vi 幾乎在任何一個 Unix Like 的機器都存在,學會他,輕鬆很多啊! 而且後來的計畫也有推出 vim 這個 vi 的進階版本,可以用的額外功能更多了! vi 是未來我們進行 shell script 程式的編寫與伺服器設定的重要工具喔! 而且是非常非常重要的工具,一定要學會才行啊! ^_^

vi 與 vim

由前面一路走來,我們一直建議使用文字模式來處理 Linux 的系統設定問題,因為不但可以讓您比較容易瞭解到 Linux 的運作狀況,也比較容易瞭解整個設定的基本精神,更能『保證』您的修改可以順利的被運作。 所以,在 Linux 的系統中使用文字編輯器來編輯您的 Linux 參數設定檔,嗯!可是一件很重要的事情呦!所以說嘛!系統管理員至少應該要熟悉一種文書處理器的!
Tips 鳥哥 這裡要再次的強調,不同的 Linux distribution 各有其不同的附加軟體,例如 Red Hat 與 Fedora 的 userconf, Linuxconf, ntsysv 與 setup 等等,而 SuSE 則有 YOU 管理工具等等, 因此,如果您只會使用此種類型的軟體來控制您的 Linux 系統時,當接管不同的 Linux distributions 時,呵呵!那可就苦惱了!
Linux是什麼 介紹中,我們知道 Linux 與 Unix 系統中的參數檔幾乎都是 ASCII 碼的『純文字』檔!因此,利用簡單的文字編輯軟體就可以馬上修改 Linux 的參數檔囉!然而,與 Windows 不同的是,如果您用慣了 Microsoft Word 或 Corel Wordperfect 的話,那麼除了 X window 裡面的編輯程式(如 xemacs )用起來尚可應付外,於 Linux 的文字模式下,會覺得檔案編輯程式都沒有 Windows 程式那麼方便。
Tips 鳥哥 還記得什麼是純文字檔嗎?忘記的話,回到 Linux 的檔案屬性與目錄配置 裡頭去瞧一瞧先~該檔案格式以 ASCII 格式碼為主。 說穿了,就是您『不論使用什麼編輯器』來開啟那個檔案時,都可以將內容給您看到,而不是呈現亂碼的檔案, 那就是純文字檔了!當您以 Windows 的 word 存一個檔案時,在 DOS 的情況下使用 type 這個指令來查閱資料,嗯!完全不知到內容是什麼?因為會出現很多的亂碼,那並非是純文字檔,而如果以 word 在存檔時,選擇『純文字類型』,嗯!那就可以使用 type 看到該檔案的內容了! 由於純文字檔在任何作業系統底下都可以被取用,是相當方便的一種設定格式啊!
無論如何,要管理好 Linux 系統時,純文字的手工設定仍是需要的!那麼在 Linux 底下有哪些文書編輯器呢? 可多了~例如 vi, emacs, xemacs, joe, e3, xedit, kedit, pico .... 多的很~ 各家處理器各有其優缺點,您當然可以選擇任何一個您覺得適用的文書處理器來使用。不過,鳥哥還是比較建議使用 vi 啦!這是因為 vi 是 Unix Like 的機器上面預設都有安裝的軟體,也就是說,您一定可以接觸到這個軟體就是了。 另外,在較新的 distributions 上,您也可以使用較新較先進的 vim 這個文書處理器! vim 可以看做是 vi 的進階軟體,他可以具有顏色顯示,很方便程式開發人員在進行程式的撰寫呢!

簡單的來說, vi 是老式的文書處理器,不過功能已經很齊全了,但是還是有可以進步的地方。 vim 則可以說是程式開發者的一項很好用的工具,就連 vim 的官方網站 (http://www.vim.org) 自己也說 vim 是一個『程式開發工具』而不是文書處理軟體~^_^。 因為 vim 裡面加入了很多額外的功能,例如支援正規表示法的搜尋架構、多檔案編輯、區塊複製等等。 這對於我們在 Linux 上面進行一些設定檔的修訂工作時,是很棒的一項功能呢!

底下鳥哥會先就簡單的 vi 做個介紹,然後再跟大家報告一下 vim 的額外功能與用法呢!

vi 的使用

基本上 vi 共分為三種模式,分別是『一般模式』、 『編輯模式』與『指令列命令模式』三種! 這三種模式的作用是:
  • 一般模式
    以 vi 處理一個檔案的時後,一進入該檔案就是一般模式了。在這個模式中, 你可以使用『上下左右』按鍵來移動游標,您可以使用『刪除字元』或『刪除整行』來處理檔案內容, 也可以使用『複製、貼上』來處理您的文件資料。

  • 編輯模式
    在一般模式中可以處理刪除、複製、貼上等等的動作,但是卻無法編輯的! 要等到您按下『i, I, o, O, a, A, r, R』等字母之後才會進入編輯模式。注意了!通常在 Linux 中,按下上述的字母時,在畫面的左下方會出現『 INSERT 或 REPLACE 』的字樣,才可以輸入任何字來輸入到您的檔案中!而如果要回到一般模式時, 則必須要按下『Esc』這個按鍵即可退出編輯模式。

  • 指令列命令模式
    在一般模式當中,輸入『 : 或 / 或 ? 』就可以將游標移動到最底下那一行,在這個模式當中, 可以提供您『搜尋資料』的動作,而讀取、存檔、大量取代字元、離開 vi 、顯示行號 等等的動作則是在此模式中達成的!
簡單的說,我們可以將這三個模式想成底下的圖示來表示之:

vi 三種模式的相互關係
圖一、 vi 三種模式的相互關係

閒話不多說,我們底下以一個簡單的例子來進行說明吧!

簡易執行範例

我們怎麼使用 vi 建立一個檔名為 test.txt 的資料呢?也是很簡單的啦, 整個步驟可以是這樣:
  1. 使用 vi 進入一般模式;
    [root@linux ~]# vi test.txt
    
    直接輸入『 vi 檔名』即可進入 vi 了!如下圖所示,左下角還會顯示這個檔案目前的狀態!如果是新建檔案會顯示 [New File],如果是已存在的檔案,則會顯示目前的檔名、行數與字元數,例如:『"/etc/man.config" 145L, 4614C』

    利用 vi 開啟一個檔案
    圖二、 利用 vi 開啟一個檔案

  2. 按下 i 進入編輯模式,開始編輯文字;

    在一般模式之中,只要按下 I, o, a 等字元,就可以進入編輯模式了!在編輯模式當中,您可以發現在左下角會出現 –INSERT- 的畫面,那就是可以輸入任意字元的提示囉!這個時候,鍵盤上除了 [Esc] 這個按鍵之外,其他的按鍵都可以視作為一般的輸入按鈕了,所以您可以進行任何的編輯囉! ( 註:在 vi 裡面, [tab] 這個按鈕所得到的結果與空白字元所得到的結果是不一樣的,特別強調一下! )

    進入 vi 的編輯模式
    圖三、 進入 vi 的編輯模式

  3. 按下 [ESC] 按鈕回到一般模式;

    好了,假設我已經按照上面的樣式給他編輯完畢了,那麼應該要如何退出呢?是的!沒錯!就是給他按下 [Esc] 這個按鈕即可!馬上你就會發現畫面左下角的 – INSERT – 不見了!

  4. 在一般模式中按下 :wq 儲存後離開 vi !

    OK,我們要存檔了,存檔並離開的指令很簡單,輸入『:wq』即可存檔離開!(注意了,按下 : 該游標就會移動到最底下一行去!)這時你在提示字元後面輸入『 ls -l 』即可看到我們剛剛建立的 test.txt 檔案啦!整個圖示有點像底下這樣:

    利用 vi 儲存檔案
    圖四、利用 vi 儲存檔案

如此一來,您的檔案 test.txt 就已經建立起來囉!很簡單吧!需要注意的是,如果您的檔案權限不對,例如為 -r--r--r-- 時,那麼可能會無法寫入,那麼可以使用『強制寫入』的方式嗎?可以!使用『:wq!』 多加一個驚嘆號即可!不過,需要特別注意呦!那個是在『您的權限可以改變』的情況下才能成立的! 關於權限的概念,請參考一下 Linux 的檔案權限概念 囉!

命令列內容說明

如前所述,所謂的命令列或命令模式,就是在最下面一行沒有顯示 『--INSERT--』或者『--REPLACE--』 字樣的時候。通常在命令列中的指令有下面幾種:(注意,當按下 『:』 時,游標會自動移動到螢幕的最下面一行!)

一般模式: 移動游標的方法
h 或 向左方向鍵(←)
游標向左移動一個字元
j 或 向下方向鍵(↓)
游標向下移動一個字元
k 或 向上方向鍵(↑)
游標向上移動一個字元
l 或 向右方向鍵(→)
游標向右移動一個字元
如果想要進行多次移動的話,例如向下移動 30 行,可以使用 "30j" 或 "30↓" 的組合按鍵, 亦即加上想要進行的次數(數字)後,按下動作即可!
[Ctrl] + [f]
螢幕『向下』移動一頁,相當於 [Page Down]按鍵 (常用)
[Ctrl] + [b]
螢幕『向上』移動一頁,相當於 [Page Up] 按鍵 (常用)
[Ctrl] + [d]
螢幕『向下』移動半頁
[Ctrl] + [u]
螢幕『向上』移動半頁
+
游標移動到非空白字元的下一列
-
游標移動到非空白字元的上一列
n<space>
那個 n 表示『數字』,例如 20 。按下數字後再按空白鍵,游標會向右移動這一行的 n 個字元。例如 20<space> 則游標會向後面移動 20 個字元距離。
0
這是數字『 0 』:移動到這一行的最前面字元處 (常用)
$
移動到這一行的最後面字元處(常用)
H
游標移動到這個螢幕的最上方那一行
M
游標移動到這個螢幕的中央那一行
L
游標移動到這個螢幕的最下方那一行
G
移動到這個檔案的最後一行(常用)
nG
n 為數字。移動到這個檔案的第 n 行。例如 20G 則會移動到這個檔案的第 20 行(可配合 :set nu)
gg
移動到這個檔案的第一行,相當於 1G 啊! (常用)
n<Enter>
n 為數字。游標向下移動 n 行(常用)
一般模式: 搜尋與取代
/word
向游標之下尋找一個字串名稱為 word 的字串。例如要在檔案內搜尋 vbird 這個字串,就輸入 /vbird 即可! (常用)
?word
向游標之上尋找一個字串名稱為 word 的字串。
n
這個 n 是英文按鍵。代表『重複前一個搜尋的動作』的意思。舉例來說, 如果剛剛我們執行 /vbird 去向下搜尋 vbird 這個字串,則按下 n 後,會向下繼續搜尋下一個名稱為 vbird 的字串。如果是執行 ?vbird 的話,那麼按下 n 則會向上繼續搜尋名稱為 vbird 的字串!
N
這個 N 是英文按鍵。與 n 剛好相反,為『反向』進行前一個搜尋動作。 例如 /vbird 後,按下 N 則表示『向上』搜尋 vbird 。
:n1,n2s/word1/word2/g
n1 與 n2 為數字。在第 n1 與 n2 行之間尋找 word1 這個字串,並將該字串取代為 word2 !舉例來說,在 100 到 200 行之間搜尋 vbird 並取代為 VBIRD 則:
『:100,200s/vbird/VBIRD/g』。
(常用)
:1,$s/word1/word2/g
從第一行到最後一行尋找 word1 字串,並將該字串取代為 word2 !(常用)
:1,$s/word1/word2/gc
從第一行到最後一行尋找 word1 字串,並將該字串取代為 word2 !且在取代前顯示提示字元給使用者確認 (confirm) 是否需要取代!(常用)
一般模式: 刪除、複製與貼上
x, X
在一行字當中,x 為向後刪除一個字元 (相當於 [del] 按鍵), X 為向前刪除一個字元(相當於 [backspace] 亦即是倒退鍵) (常用)
nx
n 為數字,連續向後刪除 n 個字元。舉例來說,我要連續刪除 10 個字元, 『10x』。
dd
刪除游標所在的那一整列(常用)
ndd
n 為數字。刪除游標所在的向下 n 列,例如 20dd 則是刪除 20 列 (常用)
d1G
刪除游標所在到第一行的所有資料
dG
刪除游標所在到最後一行的所有資料
d$
刪除游標所在處,到該行的最後一個字元
d0
那個是數字的 0 ,刪除游標所在處,到該行的最前面一個字元
yy
複製游標所在的那一行(常用)
nyy
n 為數字。複製游標所在的向下 n 列,例如 20yy 則是複製 20 列(常用)
y1G
複製游標所在列到第一列的所有資料
yG
複製游標所在列到最後一列的所有資料
y0
複製游標所在的那個字元到該行行首的所有資料
y$
複製游標所在的那個字元到該行行尾的所有資料
p, P
p 為將已複製的資料在游標下一行貼上,P 則為貼在游標上一行! 舉例來說,我目前游標在第 20 行,且已經複製了 10 行資料。則按下 p 後, 那 10 行資料會貼在原本的 20 行之後,亦即由 21 行開始貼。但如果是按下 P 呢? 那麼原本的第 20 行會被推到變成 30 行。 (常用)
J
將游標所在列與下一列的資料結合成同一列
c
重複刪除多個資料,例如向下刪除 10 行,[ 10cj ]
u
復原前一個動作。(常用)
[Ctrl]+r
重做上一個動作。(常用)
這個 u 與 [Ctrl]+r 是很常用的指令!一個是復原,另一個則是重做一次~ 利用這兩個功能按鍵,您的編輯,嘿嘿!很快樂的啦!
.
不要懷疑!這就是小數點!意思是重複前一個動作的意思。 如果您想要重複刪除、重複貼上等等動作,按下小數點『.』就好了! (常用)
進入編輯模式
i, I
插入:在目前的游標所在處插入輸入之文字,已存在的文字會向後退; 其中, i 為『從目前游標所在處插入』, I 為『在目前所在行的第一個非空白字元處開始插入』。 (常用)
a, A
a 為『從目前游標所在的下一個字元處開始插入』, A 為『從游標所在行的最後一個字元處開始插入』。(常用)
o, O
這是英文字母 o 的大小寫。o 為『在目前游標所在的下一行處插入新的一行』; O 為在目前游標所在處的上一行插入新的一行!(常用)
r, R
取代:r 會取代游標所在的那一個字元;R會一直取代游標所在的文字,直到按下 ESC 為止;(常用)
上面這些按鍵中,在 vi 畫面的左下角處會出現『--INSERT--』或『--REPLACE--』的字樣。 由名稱就知道該動作了吧!!特別注意的是,我們上面也提過了,你想要在檔案裡面輸入字元時, 一定要在左下角處看到 INSERT/REPLACE 才能輸入喔!
Esc
退出編輯模式,回到一般模式中(常用)
指令列命令模式
:w
將編輯的資料寫入硬碟檔案中(常用)
:w!
若檔案屬性為『唯讀』時,強制寫入該檔案。不過,到底能不能寫入, 還是跟您對該檔案的檔案權限有關啊!
:q
離開 vi (常用)
:q!
若曾修改過檔案,又不想儲存,使用 ! 為強制離開不儲存檔案。
注意一下啊,那個驚嘆號 (!) 在 vi 當中,常常具有『強制』的意思~
:wq
儲存後離開,若為 :wq! 則為強制儲存後離開 (常用)
:e!
將檔案還原到最原始的狀態!
ZZ
若檔案沒有更動,則不儲存離開,若檔案已經經過更動,則儲存後離開!
:w [filename]
將編輯的資料儲存成另一個檔案(類似另存新檔)
:r [filename]
在編輯的資料中,讀入另一個檔案的資料。亦即將 『filename』 這個檔案內容加到游標所在行後面
:n1,n2 w [filename]
將 n1 到 n2 的內容儲存成 filename 這個檔案。
:! command
暫時離開 vi 到指令列模式下執行 command 的顯示結果!例如
『:! ls /home』即可在 vi 當中察看 /home 底下以 ls 輸出的檔案資訊!
:set nu
顯示行號,設定之後,會在每一行的字首顯示該行的行號
:set nonu
與 set nu 相反,為取消行號!

特別注意,在 vi 中,『數字』是很有意義的!數字通常代表重複做幾次的意思! 也有可能是代表去到第幾個什麼什麼的意思。舉例來說,要刪除 50 行,則是用 『50dd』 對吧! 數字加在動作之前~那我要向下移動 20 行呢?那就是『20j』或者是『20↓』即可。

OK!會這些指令就已經很厲害了,因為常用到的指令也只有不到一半!通常 vi 的指令除了上面鳥哥註明的常用的幾個外,其他是不用背的,你可以做一張簡單的指令表在你的螢幕牆上, 一有疑問可以馬上的查詢呦!

一個案例練習

來來來!測試一下您是否已經熟悉 vi 這個指令呢?請依照底下的需求進行您的指令動作。 (底下的操作為使用 FC4 的預設檔案來進行練習的。您可以在這裡下載: http://linux.vbird.org/linux_basic/0310vi/man.config-fc4。) 看看您的顯示結果與鳥哥的結果是否相同啊?!
  1. 請在 /tmp 這個目錄下建立一個名為 vitest 的目錄;
  2. 進入 vitest 這個目錄當中;
  3. 將 /etc/man.config 拷貝到本目錄底下(或由上述的連結下載 man.config 檔案);
  4. 使用 vi 開啟本目錄下的 man.config 這個檔案;
  5. 在 vi 中設定一下行號;
  6. 移動到第 58 行,向右移動 40 個字元,請問您看到的雙引號內是什麼目錄?
  7. 移動到第一行,並且向下搜尋一下『 bzip2 』這個字串,請問他在第幾行?
  8. 接著下來,我要將 50 到 100 行之間的 man 改為 MAN,並且一個一個挑選是否需要修改,如何下達指令?
  9. 修改完之後,突然反悔了,要全部復原,有哪些方法?
  10. 我要複製 51 到 60 行這十行的內容,並且貼到最後一行之後;
  11. 刪除 11 到 30 行之間的 20 行;
  12. 將這個檔案另存成一個 man.test.config 的檔名;
  13. 去到第 29 行,並且刪除 15 個字元;
  14. 儲存後離開吧!
整個步驟可以如下顯示:
  1. 『mkdir /tmp/vitest』
  2. 『cd /tmp/vitest』
  3. 『cp /etc/man.config .』
  4. 『vi man.config』
  5. 『:set nu』
  6. 先按下『58G』再按下『40→』會看到『/dir/bin/foo』這個字樣在雙引號內;
  7. 先執行『1G』或『gg』後,直接輸入『/bzip2』,則會去到第 116 行才對!
  8. 直接下達『 :50,100s/man/MAN/gc 』即可!
  9. (1)簡單的方法可以一直按『 u 』回復到原始狀態,(2)使用不儲存離開『 :q! 』之後,再重新讀取一次該檔案;
  10. 『51G』 然後再『 10yy 』之後按下『 G 』到最後一行,再給他『 p 』貼上十行!
  11. 『11G』 之後,再給他『 20dd 』即可刪除 20 行了;
  12. :w man.test.config
  13. 『29G』 之後,再給他『 15x 』即可刪除 15 個字元;
  14. 『:wq!』
如果您的結果都可以查的到,那麼 vi 的使用上面應該沒有太大的問題啦!剩下的問題會是在…..打字練習…。

關於檔案的回復與暫存檔

另外,其實 vi 是具有『可回復』功能的呢!那麼 vi 憑什麼幫我們進行回復的功能呢? 很簡單啊!憑暫存檔啊!舉例來說,當我們編輯一個檔案時,假設名稱為 /tmp/passwd , 那麼在這個 /tmp 底下就會有一個暫存檔案,檔名為『 /tmp/.passwd.swp 』,這是一個隱藏檔, 我們所進行的一些修改都會暫時存在這個檔案當中,萬一在檔案修改過程中, 系統掛了,那麼下次你再重新 vi /tmp/passwd 時,系統就會告訴您,是否需要回復『Recovery』成修改過程中的模樣? 如果您按下 (R) ,嘿嘿!就可以將資料回復到修改過程的樣子,而不是原始檔案囉! 這是個很有用的功能喔! ^_^

這也就是說,如果有一天,您去 /tmp 底下,執行 ls -al 時,發現到底下有兩個檔案, 檔名分別為 passwd 與 .passwd.swp 的話,那麼 (1) 可能有人在編輯這個檔案; (2) 之前您在編輯這個檔案時,因為某些不知名的因素導致 vi 程式中斷,則該暫存檔就會存在。 如果是狀態 (2) ,則此時您可以將該 .passwd.swp 檔案刪除,或者是,直接 vi /tmp/passwd , 在 vi 出現是否回復時,選擇回復,然後儲存更新 /tmp/passwd ,之後再將這個 /tmp/.passwd.swp 檔案刪除即可! 如果不刪除的話,那麼每次編輯這個檔案,都會告知您該檔案有問題啊! @_@

vim 的額外功能

其實,目前大部分的 distributions 都以 vim 取代 vi 的功能了! 如果您使用 vi 後,卻看到畫面的右下角有顯示目前游標所在的行列號碼, 那麼您的 vi 已經被 vim 所取代囉~ 為什麼要用 vim 呢?因為 vim 具有顏色顯示的功能,並且還支援許多的程式語法 (syntax), 因此,當您使用 vim 編輯程式時( 不論是 C 語言,還是 shell script ), 我們的 vim 將可幫您直接進行『程式除錯 (debug)』的功能!真的很不賴吧!^_^

如果您在文字模式下,輸入 alias 時,出現這樣的畫面:
[root@linux ~]# alias
alias vi='vim'
這表示當您使用 vi 這個指令時,其實就是執行 vim 啦!如果您沒有這一行,那麼您就必須要使用 vim filename 來啟動 vim 囉!基本上, vim 的一般用法與 vi 完全一模一樣~沒有不同啦!那麼我們就來看看 vim 的畫面是怎樣囉!假設我想要編輯 /etc/man.config ,則輸入『vim /etc/man.config
#
# Generated automatically from man.conf.in by the
# configure script.
#
# man.conf from man-1.5p
#
# For more information about this file, see the man pages man(1)
# and man.conf(5).
"man.config" 138L, 4506C                               1,1          Top
上面的圖示是 vim 一畫面一角~他有幾個特色要講:
  1. 最底下一行說明這個檔案的特色,包括 138 行,共 4506 字元等等。
  2. 那個 1,1 代表目前游標在第一行的第一個字元上。您可以看到第一行有個游標的存在啊!
  3. 那個 Top 則表示,這個畫面是整個檔案的最上方!
至少就有這些資訊。而在您移動游標時,那個 1,1 的游標定位也會跟著變動,是否很方便啊! 好了,底下我們就來談一談其他 vim 的用法吧!

區塊選擇(Visual Block)

剛剛我們提到的簡單的 vi 操作過程中,幾乎提到的都是以行為單位的操作。那麼如果我想要搞定的是一個區塊範圍呢? 舉例來說,像底下這種格式的檔案:
192.168.1.1    host1.class.net
192.168.1.2    host2.class.net
192.168.1.3    host3.class.net
192.168.1.4    host4.class.net
.....中間省略......
這個檔案我將他放置到 http://linux.vbird.org/linux_basic/0310vi/hosts ,您可以自行下載來看一看這個檔案啊! 如果我想要複製的只是前面的 IP 數字部分,後面的主機名稱部分就不給他複製,那怎麼辦? 這個時候就得需要使用區塊選擇(Visual Block)的功能了。當我們按下 v 或者 V 或者 [Ctrl]+v 時, 這個時候游標移動過的地方就會開始反白,這三個按鍵的意義分別是:

區塊選擇的按鍵意義
v字元選擇,會將游標經過的地方反白選擇!
V行選擇,會將游標經過的行反白選擇!
[Ctrl]+v區塊選擇,可以用長方形的方式選擇資料
y將反白的地方複製起來
d將反白的地方刪除掉

我們以上面的 IP 對應主機名稱為範例,如果想要複製的是 IP 的話,而且僅想要前面四行, 那麼我可以:
  1. 將游標移動到第一行的第一個字元 ( 1G );
  2. 然後按下 [Ctrl]+v (按著 [ctrl] 不放,再按下 v );
  3. 然後移動方向鍵,向下向右移動數格,讓整個反白區域涵蓋 191.168.1.1 到 192.168.1.4 ;
  4. 按下 y 複製 (此時反白會自動的不見) ;
  5. 移動到任何想要插入的區域,按下 p 就可以插入剛剛複製的區塊內容!舉例來說,移動到第 1 行的第 13 個字元處按下小寫的 p ,看看會怎樣?
這個區塊選擇在已經格式的檔案中,就會顯的很有幫助喔!尤其是我們想要大量複製其中一個區塊, 而不是整行複製的場合中,就會很有用的啦!

多檔案編輯

假設一個例子,你想要將剛剛我們的 hosts 內的 IP 複製到您的 /etc/hosts 這個檔案去, 那麼該如何編輯?我們知道在 vi 內可以使用 :r filename 來讀入某個檔案的內容, 不過,這樣畢竟是將整個檔案讀入啊!如果我只是想要部分內容呢?呵呵!這個時候多檔案同時編輯就很有用了。 我們可以使用 vim 後面同時接好幾個檔案來同時開啟喔!相關的按鍵有:

多檔案編輯的按鍵
:n編輯下一個檔案
:N編輯上一個檔案
:files列出目前這個 vim 的開啟的所有檔案

這個功能也很棒啊!現在您可以做一下練習看看說!假設您要將剛剛鳥哥提供的 hosts 內的 IP 複製到您的 /etc/hosts 檔案內,那可以怎麼進行呢?可以這樣啊:
[root@linux ~]# vi hosts /etc/hosts
# 在這個檔案中利用上個小節提到的區塊選擇,按下 [ctrl]+v 來進行區塊選擇,並複製。
# 然後按下 :n 在指令列的地方輸入這玩意兒,就會轉到下一個檔案去,這個時候,
# 就可以按下 p 將剛剛複製的 IP 給貼到您的檔案中囉!如果您按下 :files ,則:


192.168.1.4 host4.class.net 192.168.1.5 host5.class.net ~ ~ :files 1 %a "hosts" line 1 2 # "/etc/hosts" line 1 Hit ENTER or type command to continue
# 看到否?在指令列輸入 :files 就可以顯示目前所編輯的檔案資訊囉!
看到了吧?利用多檔案編輯的功能,可以讓您很快速的就將需要的資料複製到正確的檔案內。 當然囉,這個功能也可以利用視窗介面來達到,那就是底下要提到的多視窗功能。

多視窗功能

想像兩個情況:
  • 當我有一個檔案非常的大,我查閱到後面的資料時,想要『對照』前面的資料, 是否需要使用 [ctrl]+f 與 [ctrl]+b 來跑前跑後查閱?
  • 我有兩個需要對照著看的檔案,不想使用前一小節提到的多檔案編輯功能;
這樣的情況下,開一個 vim 裡頭有兩個視窗的環境,就有需要啦!那麼如何開啟新視窗呢? 很簡單啊!在指令列模式輸入:『:sp {filename}』,那個 filename 可有可無, 如果想要在新視窗啟動另一個檔案,就加入檔名,否則僅輸入 :sp 時, 出現的則是同一個檔案在兩個視窗間!例如鳥哥使用 vim hosts 後,再以 :sp /etc/hosts , 結果出現如下圖示:
# Do not remove the following line, or various programs
# that require network functionality will fail.
127.0.0.1       localhost.localdomain localhost
192.168.1.11    vbird-work
192.168.1.2     vbird-server
~
/etc/hosts                   5,1            All
192.168.1.1    host1.class.net
192.168.1.2    host2.class.net
192.168.1.3    host3.class.net
192.168.1.4    host4.class.net
192.168.1.5    host5.class.net
hosts                        1,1            Top

怎樣?帥吧!兩個檔案同時在一個螢幕上面顯示,您還可以利用『[ctrl]+w+j』及『[ctrl]+w+k』 在兩個視窗之間移動呢!這樣的話,複製啊、查閱啊等等的,就變的很簡單囉~ 指令的功能有很多,不過,您只要記得這幾個就好了:

多視窗情況下的按鍵功能
:sp [filename]開啟一個新視窗,如果有加 filename, 表示在新視窗開啟一個新檔案,否則表示兩個視窗為同一個檔案內容(同步顯示)。
[ctrl]+wj按鍵的按法是:先按下 [ctrl] 不放, 再按下 w 後放開所有的按鍵,然後再按下 j ,則游標可移動到下方的視窗。
[ctrl]+wk同上,不過游標移動到上面的視窗。
[ctrl]+wq其實就是 :q 結束離開啦! 舉例來說,如果我想要結束下方的視窗,那麼利用 [ctrl]+wj 移動到下方視窗後,按下 :q 即可離開, 也可以按下 [ctrl]+wq 啊!

vim 環境設定

有沒有發現,如果我們以 vim 軟體來搜尋一個檔案內部的某個字串時,這個字串會被反白, 而下次我們再次以 vim 編輯這個檔案時,該搜尋的字串還是存在呢!甚至於, 編輯其他檔案時,如果其他檔案也存在這個字串,哇!!竟然還是主動反白耶! 另外,當我們重複編輯同一個檔案時,當第二次進入該檔案時, 游標竟然就在上次離開的那一行上頭呢!真是好方便啊~但是,怎麼會這樣呢?

這是因為我們的 vim 會主動的將您曾經做過的行為登錄下來,好讓您下次可以輕鬆的作業啊! 那個記錄動作的檔案就是: ~/.viminfo 這個檔案啦!每個人的家目錄都應該會存在這個檔案才對~這個檔案是自動產生的, 您不必自行建立。而你在 vim 裡頭所做過的動作,就可以在這個檔案內部查詢到囉~ ^_^

此外,某些 distributions 的 vim 當中,利用搜尋時,他並不會顯示反白, 有些 distributions 則會主動的幫您進行縮排的行為 (所謂的縮排, 就是當您按下 Enter 編輯新的一行時,游標不會在行首,而是在與上一行的第一個非空白字元處對齊!)。 這些其實都可以進行設定的,那就是 vim 的環境設定囉~ vim 的環境設定參數有很多,如果您想要知道目前的設定值,可以在一般模式時輸入:『 :set all 』 來查閱,不過.....設定項目實在太多了~所以,鳥哥在這裡僅列出一些平時比較常用的一些簡單的設定值, 提供給您參考啊:

vim 的環境設定參數
:set nu還記得這個吧?!就是設定行號啊!取消的話,就是 :set nonu
:set hlsearch這個就是設定是否將搜尋的字串反白的設定值。 預設值就是 hlsearch ,如果不想要反白,就 :set nohlsearch 。
:set autoindent是否自動縮排?autoindent 就是自動縮排, 不想要縮排就 :set noautoindent 。
:set backup是否自動儲存備份檔?一般是 nobackup 的, 如果設定 backup 的話,那麼當你更動任何一個檔案時,則原始檔案會被另存成一個檔名為 filename~ 的檔案。 舉例來說,我們編輯 hosts ,設定 :set backup ,那麼當更動 hosts 時,在同目錄下,就會產生 hosts~ 檔名的檔案,記錄原始的 hosts 檔案內容~
:set ruler還記得我們提到的右下角的一些狀態列說明嗎? 這個 ruler 就是在顯示或不顯示該設定值的啦!
:set showmode這個則是,是否要顯示 --INSERT-- 之類的字眼在左下角的狀態列。
:set backspace=(012)一般來說, 如果我們按下 i 進入編輯模式後,可以利用倒退鍵 (backspace) 來刪除任意字元的。 但是,某些 distribution 則不許如此。此時,我們就可以透過 backspace 來設定囉~ 當 backspace 為 2 時,就是可以刪除任意值;0 或 1 時,僅可刪除剛剛輸入的字元, 而無法刪除原本就已經存在的文字了!
:set all顯示目前所有的環境參數設定值。
:syntax (off|on)是否依據程式相關語法顯示不同顏色? 舉例來說,在編輯一個純文字檔時,如果開頭是以 # 開始,那麼該行就會變成藍色。 如果您懂得寫程式,那麼這個 :syntax on 還會主動的幫您除錯呢!但是, 如果您僅是編寫純文字檔案,要避免顏色對您的螢幕產生的干擾,則可以取消這個設定 :syntax off 。

總之,這些設定值很有用處的啦!但是......我是否每次使用 vim 都要重新設定一次各個參數值? 這不太合理吧?!沒錯啊!所以,我們可以透過設定檔來直接規定我們習慣的 vim 操作環境呢! 整體 vim 的設定值一般是放置在 /etc/vimrc 這個檔案,不過,不建議您修改他! 你可以修改 ~/.vimrc 這個檔案 (預設不存在,請您自行手動建立!),將您所希望的設定值寫入! 舉例來說,可以是這樣的一個檔案:
[root@linux ~]# vi ~/.vimrc
:set hlsearch
:set backspace=2
:set autoindent
:set ruler
:set showmode
:syntax on
這樣,當您下次重新以 vim 編輯某個檔案時,該檔案的預設環境設定就是上頭寫的囉~ 這樣,是否很方便您的操作啊!多多利用 vim 的環境設定功能呢!^_^

利用 vi 編輯前面章節的練習

我們前面提到很多的資料,例如 manupdatedb 等等的內容,對於設定檔都是簡單的提過而已。 在這裡,我們就透過 vi 的編輯功能,來直接對我們前面提到的章節來進行一些練習吧!OK!來囉~

例題一:我今天自己安裝了一套軟體,這套軟體的 man page 放置在 /opt/vbirdsoft/man 這個目錄下, 那我希望未來只要輸入類似 man vbirdcommand 就可以查閱到我這個軟體的說明文件,該如何是好?
答:
    我以 FC4 為例, FC4 的 man page 設定檔在 /etc/man.config 底下我可以找到該檔案大約 47 行的地方, 新增如下的資料:

      MANPATH   /opt/vbirdsoft/man

    儲存後離開,從此以後,就可以查詢到屬於我自己的指令的線上說明文件了。

例題二:我知道查詢檔案可以利用 locate 來進行查詢,但是, 該程式必須要配合資料庫的更新才行 (updatedb)。現在,我想讓我的 FC4 每天進行檔案資料庫的更新, 並且『不要更新 /var/cache 』這個目錄,該如何是好?
答:
    以 FC4 為例,他的 updatedb 資料庫更新設定檔在 /etc/updatedb.conf 這個檔案中。 我以 vi 開啟這個檔案後將該檔案修訂成為:

      DAILY_UPDATE=yes
      PRUNEFS="selinuxfs usbdevfs NFS nfs afs sfs smbfs cifs autofs auto iso9660 udf"
      PRUNEPATHS="/tmp /usr/tmp /var/spool/cups /var/spool/squid /var/tmp /afs /net /sfs
      /selinux /udev /media /var/cache"

    上列粗體部分為新加入的部分。那個 DAILY_UPDATE=yes 代表每日進行更新,至於 PRUNEPATHS 後面則接『不要更新的目錄』, 所以,這樣就能夠達到我們的需求囉!

例題三:在 partition 格式化的那個章節中,假設我有一個 partition 為 /dev/hdb5 , 這個 partition 掛載到 /disk2 上面,且目錄 /disk2 已經建立好了。該 partition 使用的 filesystem 為 ext3 , 請問,如果我想要在開機的時候就掛載這個 partition ,該怎麼辦?
答:
    開機掛載可以修改 /etc/fstab 這個檔案,我在這個檔案新增如下資訊即可:

      /dev/hdb5    /disk2    ext3    defaults    2    2

    這樣修改完畢後,下達 mount -a 測試看看能否正確掛載,之後就可以開機自動掛載囉~

vi 很重要的啦!上面的設定檔都與 vi 編輯有關呢!重要重要喔! ^_^

DOS 與 Linux 的斷行字元

我們在 Linux 檔案與目錄管理 談到 cat 時,曾經提到過 DOS 與 Linux 斷行字元的不同。 而我們也可以利用 cat -A 來觀察以 DOS (Windows 系統) 建立的檔案的特殊格式, 也可以發現在 DOS 使用的斷行字元為 ^M$ ,我們稱為 CR 與 LF 兩個符號。 而在 Linux 底下,則是僅有 LF ($) 這個斷行符號。這個斷行符號對於 Linux 的影響很大喔! 為什麼呢?

我們說過,在 Linux 底下的指令在開始執行時,他的判斷依據是 『Enter』,而 Linux 的 Enter 為 LF 符號, 不過,由於 DOS 的斷行符號是 CRLF ,也就是多了一個 ^M 的符號出來, 在這樣的情況下,如果是一個 shell script 的程式檔案,呵呵~將可能造成『程式無法執行』的狀態~ 因為他會誤判程式所下達的指令內容啊!這很傷腦筋吧!

那怎麼辦啊?很簡單啊,將格式轉換成為 Linux 即可啊!『廢話』,這當然大家都知道,但是, 要以 vi 進入該檔案,然後一個一個刪除 CR 嗎?當然沒有這麼沒人性啦! 我們可以透過簡單的指令來進行格式的轉換啊!
[root@linux ~]# dos2unix [-kn] file [newfile]
[root@linux ~]# unix2dos [-kn] file [newfile]
參數:
-k  :保留該檔案原本的 mtime 時間格式 (不更新檔案上次內容經過修訂的時間)
-n  :保留原本的舊檔,將轉換後的內容輸出到新檔案,如: dos2unix -n old new
範例:
範例一:將我們提供的 hosts 檔案格式更新為 dos 格式。
[root@linux ~]# unix2dos -k hosts
unix2dos: converting file hosts to DOS format ...
# 此時 hosts 這個檔案的時間不會改變,但是內容主要將斷行字元修改成為 DOS 的 CRLF 了。

範例二:將範例一已經變成 DOS 格式的 hosts 改名成為 hosts.dos ,並且轉換 Linux 
        格式到 hosts.linux
[root@linux ~]# mv hosts hosts.dos
[root@linux ~]# dos2unix -k -n hosts.dos hosts.linux
dos2unix: converting file hosts.dos to file hosts.linux in UNIX format ...
[root@linux ~]# ll
-rw-r--r--  1 root root      288 Aug  1 13:30 hosts.dos
-rw-------  1 root root      279 Aug  1 13:30 hosts.linux
# 嘿嘿!由於 DOS 格式當中多了 CR 字符,所以,檔案比較大的啦!
因為斷行字符以及 DOS 與 Linux 作業系統底下一些字符的定義不同,因此, 不建議您在 Windows 系統當中將檔案編輯好之後,才上傳到 Linux 系統,會容易發生錯誤問題。 而且,如果您在不同的系統之間複製一些純文字檔案時,千萬記得要使用 unix2dos 或 dos2unix 來轉換一下格式啊!

本章與 LPI 的關係:

http://www.lpi.org 所提供的 topic 當中, LPI 101 的 Topic 103 之 1.103.8 提到:『應試者應該能夠學會使用 vi 文書編輯器,學習的目標包含了 vi 的插入、編輯、刪除、複製與搜尋等功能的練習!』至於使用到的指令與 vi 當中所會用到的資料與指令為:
  • vi
  • /, ? (請看搜尋部分)
  • h, j, k, l (移動游標的部分,這個較常考!)
  • G, H, L (移動游標的部分)
  • i, c, d, dd, p, o, a (刪除、編輯與貼上的部分)
  • ZZ, :w!, :q!, :e!
  • :!

本章習題練習:

(要看答案請將滑鼠移動到『答:』底下的空白處,按下左鍵圈選空白處即可察看)
  • 我要在某個檔案的第 34 行向右移動 15 個字元,應該在一般模式下達什麼指令?
  • 先按下 34G 到第 34 行;
  • 再按下 [ 15 + 向右鍵 ],或 [ 15l ] 亦可!
  • 在 vi 裡面, PageDown 按鈕可以使用什麼組合鍵來取代?
  • [Ctrl] + f 可以向後翻一頁
  • 如何去到 vi 該檔案裡面的頁首或頁尾?
  • 去頁首按下 1G ;去頁尾按下  G 即可
  • 如何在一行中,移動到行頭及行尾?
  • 移動到行頭,按 0 ,移動到行尾按 $ 即可!
  • vi 裡面, r 有什麼功能?
  • 取代游標所在的那個字元
  • 如何將目前的頁面另存新檔?
  • :w filename
  • 在 linux 底下最常使用的文書編輯器為 vi ,請問如何進入編輯模式?
  • 在一般模式底下輸入: i, I, a, A 為在本行當中輸入新字元;(出現 –Insert- )
    在一般模式當中輸入: o, O 為在一個新的一行輸入新字元;
    在一般模式當中輸入: r, R 為取代字元!(左下角出現 –Replace-)
  • 如何由編輯模式跳回一般模式?
  • 可以按下[Esc]
  • 若上下左右鍵無法使用時,請問如何在一般模式移動游標?
  • [h, j, k, l]分別代表[左、下、上、右]
  • 若 [pagedown] [ pageup] 在一般模式無法使用時,如何往前或往後翻一頁?
  • 向下翻 [Ctrl] + [f]
    向前翻 [Ctrl] + [b]
  • 如何到本檔案的最後一行、第一行;本行的第一個字元、最後一個字元?
  • 分別為:G, 1G, 0, $
  • 如何刪除一行、n行;如何刪除一個字元?
  • 分別為 dd, ndd, x 或 X (dG 及 d1G 分別表示刪除到頁首及頁尾)
  • 如何複製一行、n行並加以貼上?
  • 分別為 yy, nyy, p 或 P
  • 如何搜尋 string 這個字串?
  • ?string (往前搜尋)
    /string (往後搜尋)
  • 如何取代 word1 成為 word2,而若需要使用者確認機制,又該如何?
  • :1,$s/word1/word2/g 或
    :1,$s/word1/word2/gc (需要使用者確認)
  • 如何讀取一個檔案 filename 進來目前這個檔案?
  • :r filename
  • 如何另存新檔成為 newfilename?
  • :w newfilename
  • 如何存檔、離開、存檔後離開、強制存檔後離開?
  • :w; :q: :wq; :wq!
  • 在 vi 底下作了很多的編輯動作之後,卻想還原成原來的檔案內容,應該怎麼進行?
  • 直接按下 :e! 即可恢復成檔案的原始狀態!
  • 我在 vi 這個程式當中,不想離開 vi ,但是想執行 ls /home 這個指令,vi 有什麼額外的功能可以達到這個目的:
  • 事實上,可以使用[ :! ls /home ]不過,如果你學過後面的章節之後,你會發現,執行[ ctrl + z ]亦可暫時退出 vi 讓你在指令列模式當中執行指令喔!
  • 如何設定與取消行號?
  • :set nu
    :set nonu

參考資料

修改歷史:
  • 2002/04/05:第一次完成
  • 2003/02/07:重新編排與加入 FAQ
  • 2003/02/25:新加入本章節與 LPI 的相關性說明!
  • 2005/07/28:將舊文章移動到 這裡
  • 2005/08/01:加入果正兄文章的參考,還有查閱 vim 官方網站的資料!
伺服器篇文件
各版本彙整說明
CentOS 6.x