VIM編輯器的宏操作

2022-07-19 06:01:26

這兩天看到一個小練習,要求如下:

在GVIM下,將下面這張圖的內容

改成下面這樣

並且指出,要用批次操作的方式,不能一行一行的鍵入

其實第一反應是利用正規表示式來操作,但是讓用正規表示式以外的操作方式,查了不少方法,最終發現了VIM的宏,覺得挺有意思的,特地記錄一下

宏的基本操作

宏是用來重複執行一組操作的

操作方式為

1、在普通模式下,按q 開啟宏操作方式

2、隨後輸入一個宏名作為暫存器,為了方便,可以輸入一個小寫字母,但不要用大寫字母喲

3、輸入要批次操作的內容,VIM會將此時所有的操作記錄在暫存器中

4、操作完成後,再次在普通模式下按q 結束宏記錄

5、之後可以呼叫宏操作,呼叫方式有兩種,一種是在普通模式下按@宏名,另一種方式是在命令模式下輸入normal @宏名

下面一步步演示

先是在普通模式下依次按下qa,其中a是我們的宏名

完成這一步可以看到在VIM視窗的左下角出現了記錄中字樣,表明隨後的操作都將記錄在VIM的宏中

隨後,我們按下i進入輸入模式,並輸入

number <回車>

Esc退出輸入模式,再按q,退出宏操作

此時便完成了宏記錄操作,記錄完宏操作後是這樣的

接下來分別用兩種方式呼叫宏

普通模式下,直接輸入@a

可以看到多出了一行內容,用命令列方式呼叫

在命令列輸入
:normal @a

可以看到,再次輸入了一行內容

如果想知道宏名中有哪些操作,可以在命令模式下輸入

:register @a

可以看到剛才記錄在宏名a中操作全部展示出來了

為什麼不建議宏名用大寫字母

我們新建一個VIM文字,按照同樣的方式操作一下,只是將宏名由a換成A

我們先來檢視一下宏名A中的內容

可以看到,宏中並沒有任何操作,大寫字母的作用是在現有宏中新增操作的

對一個現有的宏,如果我們想修改裡面的操作,如果我們按照

q
a
<一系列操作>
q

這個方式操作只會覆蓋掉原有的宏,並不會在原有宏的基礎上增加操作

接下我們試試在最初的宏a中加上is 0,用a進入和A進入分別會發生什麼

#方式1
q
a
輸入 is 0
q

可以看到,執行宏操作後,只列印出is 0,再來看看此時宏a中的內容

可以看到此時的宏中只有is 0

先將宏改回原來的樣子,再來換一種方式試試

#方式2
q
A
輸入 is 0
q

可以看到此時呼叫宏時,不僅有列印出了number也列印出了is 0,最後再看看這種方式更改後宏a中記錄的操作

宏中設定變數

有時我們會用到變數,而宏中也可以設定變數,操作方式如下

在進入宏記錄後,在命令列輸入
:let i = 1  <回車>
按 i 進入輸入模式
按Ctrl  r  = 三個按鍵
在輸入變數名 i 即可插入變數

我們按照這個步驟試一下,過程如下

q
b
:let i = 1 <回車>
進入輸入模式,並輸入Ctrl r =  i <回車>
退出輸入模式,並結束宏記錄
普通模式下按下 @b

不過有一點要說明,在一個VIM文字中,所有的變數是共同有的,我們對宏a進行一個更改

在宏a後面加上
value Ctrl r =  i <回車>

可以看到在宏b中設定的變數在宏a中依舊可以呼叫

如果我們對變數 i不斷進行累加,可以在宏a中加入let i = i + 1

此時,我們也可以在其他宏中更改變數i,比如我們新建一個宏,如下:

q
c
在命令列輸入
:let i = 10 <回車>
q
普通模式下輸入 @a

可以看到此時i的值是10,我們再次在普通模式下按@a

可以看到此時是在10的基礎上進行累加的

如果,我們再新建一個宏,更改變數i的變化方式呢,就像下面這樣

q
m
命令列輸入  :let i = i + 50 <回車>
q
普通模式下按 @a

可以看到只有第一次呼叫宏時是按照宏m的設定變化的,但隨後又按照宏a的設定變化


下面給出最初的小練習的解決方案

/*	在宏中設定變數	*/
q
a
:let i = 1 <回車>
:let j = 2 <回車>
q

/*	在宏中鍵入內容	*/
q
a
i
number 組合鍵 i + number 1 = number 組合鍵 j <回車>
ESC
:let i = i + 1 <回車>
:let j = j + 1 <回車>
q

/*	列印	*/
普通模式下輸入  20@a

其實利用正規表示式的方式也是能夠實現的,正則表達的方式下次貼出來