sed是Stream Editor(字符流編輯器)的縮寫,簡稱流編輯器。sed是操做、過濾和轉換文本內容的強大工具。經常使用功能包括對文件實現快速增刪改查(增長、刪除、修改、查詢),其中查詢的功能中最經常使用的兩大功能是過濾(過濾指定字符串)、取行(取出指定行)html
sed經過執行下面的循環來操做輸入流中的每一行: 首先,sed讀取輸入流中的一行,移除該行的尾隨換行符,並將其放入到pattern space中。而後對pattern space中的內容執行SCRIPT中的sed命令,每一個sed命令均可以關聯一個地址:地址是一種條件判斷代碼,只有符合條件的行纔會執行相應的命令。當執行到SCRIPT(指的是咱們定義的操做)的尾部時,除非指定了"-n"選項,不然pattern space中的內容將寫到標準輸出流中,並添加回尾隨的換行符。而後進入下一個循環開始處理輸入流中的下一行。linux
但有些特殊命令(如"D"命令)會進入多行模式,使得SCRIPT循環結束 時將數據鎖在pattern space中不輸出也不清空,甚至在SCRIPT循環還沒結束時就強行進入下一 輪SCRIPT循環,其實就至關 於在上面的while循環結構中加上了"continue"關鍵字。此外還有命令(如"d")能夠直接退出 SCRIPT循環進入下一個sed循環,就像是在while循環中加上了"break"同樣。甚至還有直接退出 sed循環的命令(只有2個這樣的命令:"q"和"Q"),就像是加上了"exit"同樣。正則表達式
sed的執行過程是一個循環的過程:bash
命令格式:app
sed的命令格式:sed [options] 'command' file(s); sed的腳本格式:sed [options] -f scriptfile file(s);
基本選項以下:編輯器
-e :直接在命令行模式上進行sed動做編輯,此爲默認選項; -f :將sed的動做寫在一個文件內,用–f filename 執行filename內的sed動做; -i :直接修改文件內容,sed是經過建立一個臨時文件並將輸入寫入到該臨時文件,而後重命名爲源文件來實現的 -n :只打印模式匹配的行; -r :支持擴展表達式,sed所支持的擴展正則表達式和egrep同樣 -s : 考慮爲多個單獨的文件,而不是把多個文件做爲一個流進行輸入 -h或--help:顯示幫助; -V或--version:顯示版本信息。
實例練習:首先咱們準備文件test.txt,內容以下工具
1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。
[root@lgh test]# sed -n '3p' test.txt #打印第三行 3、I did my homework and watched TV。 On Sunday morning , [root@lgh test]# sed '=' test.txt #打印行號 1
1、Last weekend, I was busy。 2
2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3
3、I did my homework and watched TV。 On Sunday morning , 4
4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5
5、It was fun 。I had a very happy weekend。 [root@lgh test]# sed -r -n '/[a-z]*ing/p' test.txt #正則匹配ing字符串 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning ,
這裏所說的地址選擇就是咱們要處理一個文檔中的哪些行?好比第1行到第3行,這就是用來選擇匹配咱們須要進行處理的行。spa
當sed將輸入流中的行讀取到模式空間後,就須要對模式空間中的內容進行匹配,若是能匹配就能執行對應的命令,若是不能匹配就直接輸出、清空模式空間並進入下一個sed循環讀取下一行。
定址表達式有多種,其格式爲[ADDR1][,ADDR2]。這能夠分爲3種方式:.net
'NUMBER':指定一個行號,sed將僅只匹配該行。(須要注意,除非使用了"-s"或"-i"選項,sed將對全部輸入文件的行連續計數。)
'FIRST~STEP':FIRST和STEP都是非負數。該定址表達式表示從第FIRST行開始,每隔STEP行就再取一次。要選擇全部的奇數行,使用「1~2」;
'$':該符號匹配的是最後一個文件的最後一行,若是指定了"-i"或"-s",則匹配的是每一個文件的最後一行。
'/REGEXP/':該定址表達式將選擇那些能被正則表達式REGEXP匹配的全部行。若是REGEXP中自身包含了字符"/",則必須使用反斜線進行轉義,即"\/"。
'/REGEXP/I':正則表達式的修飾符"I"是GNU的擴展功能,表示REGEXP在匹配時不區分大小寫。
'/REGEXP/M':可讓sed直接匹配多行模式下(multi-line mode)的位置。該修飾符使得正則表達式的元字符"^"和"$"匹配分別匹配每一個新行後的空字符和新行前的空字符。還有另外兩個特殊的字符序列(\`和\',分別是反斜線加反引號,反斜線加單引號),它們老是匹配buffer空間中的起始和結束位置。此外,元字符點"."不能匹配多行模式下的換行符。
(注:在單行模式下,使用M和不使用M是沒有區別的,但在多行模式下各符號匹配的位置將和一般的正則表達式元字符匹配的內容不一樣,各符號的匹配位置以下圖所示)
'0,/REGEXP/':使用行號0做爲起始地址也是支持的,就像此處的"0,/REGEXP/",這時sed會嘗試對第一行就匹配REGEXP。換句話說,"0,/REGEXP/"和"1,/REGEXP/"基本是相同的。但以行號0做爲起始行時,若是第一行就能被ADDR2匹配,範圍搜索當即就結束,由於第二個地址已經搜索到了;若是以行號1做爲起始行,會從第二行開始匹配ADDR2,直到匹配成功。
'ADDR1,+N':匹配ADDR1和其後的N行。
'ADDR1,~N':匹配ADDR1和其後的行直到出現N的倍數行,倍數可爲隨意整數倍。 (注:能夠是任意倍,只要N的倍數是最接近且大於ADDR1的便可。如ADDR1=1,N=3匹配1到3行,ADDR1=5,N=4匹配5-8行。命令行
注意:sed採用計數器計算,每讀取一行,計數器加1,直到最後一行。所以在讀到最後一行前,sed是不知道此次輸入流中總共有多上行,也不知道最後一行是第幾行。"$"符號表示最後一行,它只是一個特殊的標識符號。當sed讀取到輸入流的尾部時,sed就會爲該行打上該標記。沒法使用"$"參與數學運算,例如沒法使用$-1表示倒數第二行,由於sed在讀到最後一行前,它並不知道這是倒數第二行,此時也還沒打"$"標記,所以$-1是錯誤的定址表達式。另外一方面,sed只能經過一次輸入流,這意味着已經讀取過的行沒法再次被讀取,因此sed不提供往回取數據的定址表達式
經常使用的正則匹配模式:
^ 匹配行開始,如:/^sed/匹配全部以sed開頭的行; $ 匹配行結束,如:/sed$/匹配全部以sed結尾的行; . 匹配一個非換行符的任意字符,如:/s.d/匹配s後接一個任意字符,最後是d; * 匹配0個或多個字符,如:/*sed/匹配全部模板是一個或多個空格後緊跟sed的行; [] 匹配一個指定範圍內的字符,如/[ss]ed/匹配sed和Sed; [^] 匹配一個不在指定範圍內的字符,如:/[^A-RT-Z]ed/匹配不包含A-R和T-Z的一個字母開頭,緊跟ed的行; \(..\) 匹配子串,保存匹配的字符,如s/\(love\)able/\1rs,loveable被替換成lovers; & 保存搜索字符用來替換其餘字符,如s/love/**&**/,love這成**love**; \< 匹配單詞的開始,如:/\ \> 匹配單詞的結束,如/love\>/匹配包含以love結尾的單詞的行; x\{m\} 重複字符x,m次,如:/0\{5\}/匹配包含5個0的行; x\{m,\} 重複字符x,至少m次,如:/0\{5,\}/匹配至少有5個0的行; x\{m,n\} 重複字符x,至少m次,很少於n次,如:/0\{5,10\}/匹配5~10個0的行;
實例 :
[root@lgh test]# sed -n 1,3p test.txt #輸出1-3行 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , [root@lgh test]# sed -n 1p test.txt #輸出第一行 1、Last weekend, I was busy。 [root@lgh test]# sed -n 1,/On/p test.txt #輸出第一行到匹配到On字符串的行 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, [root@lgh test]# sed -n 1,/[a-z]*ing/p test.txt #輸出第一行到匹配到ing字符串的行 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, [root@lgh test]# sed -r -n 1,/[a-z]*ing/p test.txt 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, [root@lgh test]# sed -r -n 1,+2p test.txt #輸出從第一行開始以及後兩行 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , [root@lgh test]# sed -n 1,~2p test.txt #從第一行開始輸出到2的倍數行 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, [root@lgh test]# sed -n 3,~2p test.txt #從第3行開始輸出到2的倍數行 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 [root@lgh test]# sed -n 1~2p test.txt #輸出從第一行開始,步長爲的2的行 1、Last weekend, I was busy。 3、I did my homework and watched TV。 On Sunday morning , 5、It was fun 。I had a very happy weekend。 [root@lgh test]# sed -n /on/I,/with/Ip test.txt #輸出匹配on到with的行,忽略大小寫 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。
咱們知道匹配到咱們須要操做的行的時候,開始進行咱們須要的操做,請繼續看下文
經常使用命令以下:
a 在當前行下面插入文本; i 在當前行上面插入文本; c 把選定的行改成新的文本; d 刪除,刪除選擇的行; D 刪除模板塊的第一行; s 替換指定字符; h 拷貝模板塊的內容到內存中的緩衝區; H 追加模板塊的內容到內存中的緩衝區; g 得到內存緩衝區的內容,並替代當前模板塊中的文本; G 得到內存緩衝區的內容,並追加到當前模板塊文本的後面; l 列表不能打印字符的清單; n 讀取下一個輸入行,用下一個命令處理新的行而不是用第一個命令; N 追加下一個輸入行到模板塊後面並在兩者間嵌入一個新行,改變當前行號碼; p 打印模板塊的行。 P(大寫) 打印模板塊的第一行; q 退出Sed; b lable 分支到腳本中帶有標記的地方,若是分支不存在則分支到腳本的末尾; r file 從file中讀行; t label if分支,從最後一行開始,條件一旦知足或者T,t命令,將致使分支到帶有標號的命令處,或者到腳本的末尾; T label 錯誤分支,從最後一行開始,一旦發生錯誤或者T,t命令,將致使分支到帶有標號的命令處,或者到腳本的末尾; w file 寫並追加模板塊到file末尾; W file 寫並追加模板塊的第一行到file末尾; ! 表示後面的命令對全部沒有被選定的行發生做用; = 打印當前行號; # 把註釋擴展到下一個換行符之前;
一、強制輸出命令p
默認狀況下sed會輸出全部的行,使用-n能夠禁用默認的輸出,而後使用p指定本身想輸出的行。
[root@lgh test]# sed 1,2p test.txt #沒事使用-n,因此1,2行重複答應,兩種輸出模式不衝突 1、Last weekend, I was busy。 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。 [root@lghtest]# sed -n 1,2p test.txt #輸出1,2行 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon,
二、刪除命令d
命令"d"用於刪除整個模式空間中的內容,並當即退出當前SCRIPT循環,進入下一個sed循環,即讀取下一行
[root@lgh test]# sed 3,5d test.txt #刪除第3行到第5行的數據 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon,
修改test.txt內容以下:
#!/bin/bash #test 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。
[root@lghtest]# sed '/^#/{1!d}' test.txt #刪除以#開頭的行,第一行例外 #!/bin/bash 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。
若是"d"後面還有命令,在刪除模式空間後,這些命令不會執行,由於會當即退出當前SCRIPT循環
三、退出命令q或者Q
"q"和"Q"命令的做用是當即退出當前sed程序,使其再也不執行後面的命令,也再也不讀取後面的行。所以,在處理大文件或大量文件時,使用"q"或"Q"命令能提升很大效率。它們之間的不一樣之處在於"q"命令被執行後還會使用自動輸出動做輸出模式空間的內容,除非使用了"-n"選項。而"Q"命令則會當即退出,不會輸出模式空間內容。另外,能夠爲它們指定退出狀態碼,例如"q 1"
[root@lgh test]# sed '3q' test.txt #輸出錢3行,相似 head -3 #!/bin/bash #test 1、Last weekend, I was busy。 [root@lgh test]# sed -n '/[a-z]*ing/{p;q}' test.txt #找到一條ing的字符串,輸出並退出 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon,
四、輸出行號=
"="命令用於輸出最近被讀取行的行號。在sed內部,使用行號計數器進行行號計數,每讀取一行,行號計數器加1。
[root@lgh test]# sed -n '/[a-z]*ing/{p;=;q}' test.txt #找到一條ing的字符串,輸出行並輸出行號,而後退出 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 4
五、字符一一對應替換命令"y"
該命令和"tr"命令的映射功能同樣,都是將字符進行一一替換
[root@lghtest]# sed 'y/ing/ING/' test.txt #把文檔中的ing一一對應替換成ING #!/bIN/bash #test 1、Last weekeNd, I was busy。 2、ON Saturday morNING, my classmate aNd I had Math traINING class。 Saturday afterNooN, 3、I dId my homework aNd watched TV。 ON SuNday morNING , 4、I weNt to HaNG zhou MeteorolGIcal ExperIeNce Hall wIth my famIly。 5、It was fuN 。I had a very happy weekeNd。
六、讀取下一行命令"n"
在sed的循環過程當中,每一個sed循環的第一步都是讀取輸入流的下一行到模式空間中,這是咱們沒法控制的動做。但sed有讀取下一行的命令"n"。
[root@lgh test]# sed -n '/[a-z]*ing/{p;n;p}' test.txt #輸出匹配到ing字符串的一行和下一行 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , [root@lgh test]# sed -n '/[a-z]*ing/{p;n;n;p}' test.txt #輸出匹配到ing字符串的一行和下下行 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 4、I went to Hang zhou Meteorolgical Experience Hall with my family。
七、替換命令s
命令格式:s/REGEXP/REPLACEMENT/FLAGS
功能就是替換,首先須要匹配,而後再替換,經常使用的選項以下:
g 表示行內全面替換; p 表示打印行; \1 子串匹配標記; & 已匹配字符串標記;
修改test.txt的內容以下:
#!/bin/bash #test test1 test2 test3 #test4 test5 test6 test7 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。
[root@lgh test]# sed -n 's/test/TEST/p' test.txt #替換並打印,默認替換第一列 #TEST test1 test2 test3 #TEST4 test5 test6 test7 [root@lgh test]# sed -n 's/test/TEST/gp' test.txt #全局替換 #TEST TEST1 TEST2 TEST3 #TEST4 TEST5 TEST6 TEST7 [root@lgh test]# sed -n 's/test/TEST/2p' test.txt #指定列替換 #test TEST1 test2 test3 #test4 TEST5 test6 test7
[root@lgh test]# sed -n '5,$s/ing/***&***/p' test.txt #給匹配到的字符串添加* 2、On Saturday morn***ing***, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morn***ing*** , [root@lgh test]# sed -n '5,$s/^/#/p' test.txt #在第5行到最後一行添加註釋 #2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, #3、I did my homework and watched TV。 On Sunday morning , #4、I went to Hang zhou Meteorolgical Experience Hall with my family。 #5、It was fun 。I had a very happy weekend。
[root@mvxl2685 test]# echo 'cmd1 && cmd2 || cmd3' | sed 's%&&\(.*\)||\(.*\)%\&\&\2||\1%' #cmd1 && cmd2 || cmd3"的cmd2和cmd3命令對調個位置 cmd1 && cmd3|| cmd2
八、追加(a)、插入(i)、修改(c)
三種格式是"[a|i|c] TEXT",表示將TEXT內容隊列化到內存中,當有輸出流或者說有輸出動做的時候,半路追上輸出流,分別追加、插入和替換到該輸出流而後輸出。追加是指追加在輸出流的尾部,插入是指插入在輸出流的首部,替換是指將整個輸出流替換掉。"c"命令和"a"、"i"命令有一絲不一樣,它替換結束後當即退出當前SCRIPT循環,並進入下一個sed循環,所以"c"命令後的命令都不會被執行。
[root@mvxl2685 test]# sed '/ing/a good job' test.txt #在匹配行後面追加 #!/bin/bash #test test1 test2 test3 #test4 test5 test6 test7 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, good job 3、I did my homework and watched TV。 On Sunday morning , good job 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。 [root@mvxl2685 test]# sed '/ing/i good job' test.txt #在匹配行前面插入 #!/bin/bash #test test1 test2 test3 #test4 test5 test6 test7 1、Last weekend, I was busy。 good job 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, good job 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。 [root@mvxl2685 test]# sed '/ing/c good job' test.txt #修改匹配行 #!/bin/bash #test test1 test2 test3 #test4 test5 test6 test7 1、Last weekend, I was busy。 good job good job 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。
九、多行模式命令"N"、"D"、"P"
[root@mvxl2685 test]# cat test.txt #查看文件內容 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。 [root@mvxl2685 test]# sed -n 'n;p' test.txt
#首先把第一行加載到模式空間,而後執行n,把第二行加載到模式空間,覆蓋了第一條,而後執行p進行打印,輸出第2條數據,繼續自動加載第3條到模式空間,執行n,加載第4條覆蓋第3條,輸出第4條 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 [root@mvxl2685 test]# sed -n 'N;p' test.txt
#加載第一條到模式空間,執行N,把第2條也加載進去,執行p,一塊兒答應兩條,而後接着加載3,N命令加載4,p打印兩條,接着加載5,N命令執行爲空,到了尾部,直接結束sed命令 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 [root@mvxl2685 test]# sed -n '$!N;p' test.txt
#加載第一條到模式空間,執行N,把第2條也加載進去,執行p,一塊兒答應兩條,而後接着加載3,N命令加載4,p打印兩條,接着加載5,到了尾部,跳過N命令,執行p,打印第5條 1、Last weekend, I was busy。 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 5、It was fun 。I had a very happy weekend。 [root@mvxl2685 test]# sed -n '$!N;P' test.txt
#加載第一條到模式空間,執行N,把第2條也加載進去,執行P,這裏只打印\n前的數據,也就是第一條,而後接着加載3,覆蓋模式空間,N命令加載4,P打印第3條,接着加載5,到了尾部,跳過N命令,執行P,打印第5條 1、Last weekend, I was busy。 3、I did my homework and watched TV。 On Sunday morning , 5、It was fun 。I had a very happy weekend。 [root@mvxl2685 test]# sed 'N;D' test.txt
#加載第一條到模式空間,執行N,加載第二條到模式空間,D刪除\n前面的數據,保留第二條,而後加載第三條,刪除第二條,依次類推, 5、It was fun 。I had a very happy weekend。
[root@mvxl2685 test]# sed -n '/training/{N;p}' test.txt #打印匹配行以及下一行 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 3、I did my homework and watched TV。 On Sunday morning , [root@mvxl2685 test]# sed -n '/training/{N;s/\n//;p}' test.txt #合併兩行 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon,3、I did my homework and watched TV。 On Sunday morning , [root@mvxl2685 test]# sed -n '/training/{N;s/\n//p}' test.txt #合併兩行 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon,3、I did my homework and watched TV。 On Sunday morning ,
十、buffer空間數據交換命令"h"、"H"、"g"、"G"、"x"
sed除了維護模式空間(pattern space),還維護另外一個buffer空間:保持空間(hold space)。這兩個空間初始狀態都是空的。
絕大多數時候,sed僅依靠模式空間就能達到目的,但有些複雜的數據操做則只能藉助保持空間來實現。之因此稱之爲保持空間,是由於它是暫存數據用的,除了僅有的這幾個命令外,沒有任何其餘命令能夠操做該空間,所以藉助它能實現數據的持久性。
保持空間的做用很大,它和模式空間之間的數據交換能實現不少看上去不能實現的功能,是實現sed高級功能所必須的,經常使用的幾個命令以下:
注意,不管是交換、追加仍是覆蓋,原空間的內容都不會被刪除。
可能理解起來不是很好理解,畫個圖就輕鬆易懂了:
在sed處理文件的時候,每一行都被保存在一個叫模式空間的臨時緩衝區中,除非行被刪除或者輸出被取消,不然全部被處理的行都將打印在屏幕上。接着模式空間被清空,並存入新的一行等待處理。
[root@mvxl2685 test]# sed -n '/training/p' test.txt #打印匹配的行 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, [root@mvxl2685 test]# sed -n '/training/{h;n;G;p}' test.txt #打印匹配的行和下一行,並交換位置 3、I did my homework and watched TV。 On Sunday morning , 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, [root@mvxl2685 test]# sed -n '/training/{h;G;p}' test.txt #兩次打印匹配的行 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon,
[root@mvxl2685 test]# sed '1!G;h;$!d' test.txt #逆序打印文件 5、It was fun 。I had a very happy weekend。 4、I went to Hang zhou Meteorolgical Experience Hall with my family。 3、I did my homework and watched TV。 On Sunday morning , 2、On Saturday morning, my classmate and I had Math training class。 Saturday afternoon, 1、Last weekend, I was busy。
逆序打印思路以下:
參考地址:
http://www.javashuo.com/article/p-uvzpegog-cs.html
http://www.javashuo.com/article/p-uvfvsvqf-ce.html
https://www.linuxprobe.com/linux-sed-command.html
https://blog.csdn.net/weixin_38149264/article/details/78074300
https://blog.csdn.net/yangbin1265712/article/details/82994666