常用來配合 Regular Expression 的指令有 grep、swk、sed、vi、less,不過下列提到的 Regular Expression 字元與之前提到的萬用字元不同,且建議使用 Regular Expression 時前後使用單或雙引號括住。例如使用者帳號中有 wei 及 weithenn 若我們想使用 grep 來尋找 wei 使者用帳號則會連 weithenn 使用者帳號也一併列出,此時我們便可利用 Anchors (定錨點) 來配合處理。
#grep wei /etc/passwd
weithenn:x:500:500::/home/user/weithenn:/bin/bash
wei:x:501:501::/home/user/wei:/bin/bash
我們透過 Anchors (定錨點) 來指定搜尋 /etc/passwd 內容時僅搜尋開頭為 wei: 內容。
#grep '^wei:' /etc/passwd
wei:x:501:501::/home/user/wei:/bin/bash
知道了 Regular Expression 好用之處後開始介紹常用的過濾字元
萬用字元 (Wildcard Characters)
.: any single char
[abc]: char in set
[a-c]: char in range
[^abc]: not in set
[^a-c]: not in range
修改 (Modifies)
*: zero or more previous-char (有或沒有都可以)
\+: one or more previous-char (至少 1 個)
\?: zero or one previous-char
\{i \}: i 個 previous-char
\{i,\}: 比 i 多 previous-char
定錨點(Anchors)
^: line begin with
$: line end with
\<: word begin with
\>: word end with
----- Wildcard Characters (萬用字元) 練習 -----
檔案 people 中有五個人名分別為 chris、christina、chloe、wei、weithenn 利用上述的 Wildcard Characters (萬用字元) 來對其搜尋內容進行過濾。
#cat employee
chris
christina
chloe
wei
weithenn
#grep ch employee //搜尋開頭為 ch 相關名字
chris
christina
chloe
#grep wei. employee //搜尋開頭為 wei 後接任一字元 (any single char)
weithenn
#grep ch[a-m] employee //搜尋開頭為 ch 後面字元為 a ~ m 之間的字元 (char in range)
chloe
#grep ch[^a-m] employee //搜尋開頭為 ch 後面字元排除 a ~ m 之間的字元 (not in range)
chris
christina
#grep ch[r] employee //搜尋開頭為 ch 後面字元為 r 的字元 (char in set)
chris
christina
#grep ch[lr] employee //搜尋開頭為 ch 後面字元為 l、r 的字元 (char in set)
chris
christina
chloe
----- Modifies 練習 -----
檔案 xyz 中分別有不同字串長度的 x、y、z,利用 Modifies 來對其搜尋內容進行過濾。
#cat xyz
x
xx
xxx
y
yy
yyy
z
zz
zzz
xyz
xxyyzz
zyxxyz
#grep "x*" xyz //搜尋 x 後面字元為 0 個 x 或以上的其它字元
x
xx
xxx
y
yy
yyy
z
zz
zzz
xyz
xxyyzz
zyxxyz
#grep "x\+" xyz //搜尋開頭為 x 後面字元為 1 個 x 或以上的字元
x
xx
xxx
xyz
xxyyzz
zyxxyz
#grep "x\?yz" xyz //搜尋為 x 與 yz 中間字元為 0 或 1 個以上的其它字元
xyz //符合 0 個字元 xyz
xxyyzz //符合 1 個字元 xyyz
zyxxyz //符合 1 個字元 xxyz
#grep "x\{2\}" xyz //搜尋 2 個(含) x 字元的字串 (i 個 previous-char)
xx
xxx
xxyyzz
zyxxyz
#grep "x\{3,\}" xyz //搜尋 3 個(含) x 字元的字串 (比 i 多 previous-char)
----- Anchors (定錨點) 練習 -----
檔案 bad 中分別有不同字串長度的文字,利用 Anchors (定錨點) 來對其搜尋內容進行過濾。
#cat baby //檔案 baby 內容
baby
babylon
babysitter
#grep "^ba" baby //搜尋檔案中每行開頭為 ba 的字串 (line begin with)
baby
babylon
babysitter
#grep "er$" baby //搜尋檔案中每行結尾為 er 的字串 (line end with)
babysitter
#grep "^baby$" baby //搜尋檔案中每行開頭及結尾為 bad 的字串
baby
#grep "\<ba" baby //搜尋檔案中含有 ba 開頭的字串 (word begin with)
baby
babylon
babysitter
#grep "on\>" baby //搜尋檔案中含有 on 結尾的字串 (word end with).
babylon
最後來個 Regular Expression 綜合練習,查詢檔案內容中取出您要的條件字串
#cat test //列出檔案 test 內容
123456789012345678901234567890
abcdefghij12345678
www.weithenn.org
aaaaabbbbbcccccdddddeeeee
aaaaa tw.yahoo.com deeeee
weithenn
chris
#grep '^[a-z 0-9]\{5\}$' test //搜尋字串開頭為 a ~ z 及 0 ~ 9 結尾的字串且字元數為 5
chris
#grep '^[a-z 0-9]ww' test //搜尋字串開頭為 a ~ z 及 0 ~ 9 字串文字開頭為 w
www.weithenn.org
#grep 'n[a-z 0-9]$' test //搜尋字串結尾為 a ~ z 及 0 ~ 9 結尾的字串文字為 n
weithenn
----- Windows 與 Unix-Like 檔案格式轉換 (dos2unix、unix2dos) -----
由於 Windows 與 Unix-Like 對於內容中 換行字元 的處理方式不同,因此便會發生您在 Windows 上修改好檔案內容而上傳至 Unix-Like 環境執行時發生問題,此時便為換行符號所導致,這時便可利用簡單的指令來進行檔案格式內換行字元的轉換,我們可使用 cat -A 來對檔案進行查看檔案內容即可知為 Windows 格式或 Unix-Like 格式,如下檔案 f1 為 Unix-Like 格式而 f2 為 Windows 格式可發現其換行字元的不同。
#cat -A f1 //Unix-Like 格式
a$
b$
c$
d$
e$
#cat -A f1 //Windows 格式
a^M$
b^M$
c^M$
d^M$
e^M$
我們也可透過指令 od 來查看檔案的 ASCII 碼,可發現 Unix-Like 格式其換行字元為 \n (10 New Line) 而 Windows 格式其換行字元為 \r \n (13 Carriage Return 及 10 New Line) 所組成。
#od -t c f1
0000000 a \n b \n c \n d \n e \n
0000012
#od -t c f1
0000000 a \r \n b \r \n c \r \n d \r \n e \r \n
0000017
因此我們可以使用指令 dos2unix、unix2dos 顧名思義這二個指令即對檔案內容的換行字元進行處理。
#cat -A f1 //Unix-Like 格式
a$
b$
c$
d$
e$
#unix2dos f1 //執行轉換換行字元指令 (Unix-Like -> Windows)
unix2dos: converting file f1 to DOS format ...
#cat -A f1 //Windows 格式
a^M$
b^M$
c^M$
d^M$
e^M$
#dos2unix f1 //執行轉換換行字元指令 (Windows -> Unix-Like)
dos2unix: converting file f1 to UNIX format ...
#cat -A f1 //Unix-Like 格式
a$
b$
c$
d$
e$
(上一篇)邁向 RHCE 之路 (Day08) - 標準輸入及輸出、管線
(下一篇)邁向 RHCE 之路 (Day10) - vi 編輯器及常用指令
邁向 RHCE 之路系列文章連結
拍謝,好像有些問題耶。像是下面這個例子,明明指令一樣,但是意義卻不一樣。還有其他部分,寫的是x,講的卻是a。請明察。
#grep ch[^a-m] employee //搜尋開頭為 ch 後面字元為 a ~ m 之間的字元 (char in range)
chloe
#grep ch[^a-m] employee //搜尋開頭為 ch 後面字元排除 a ~ m 之間的字元 (not...(恕刪)
非常感謝 chiounan 指正已經修正完畢,因為發表文章的框框太小,我又常常因為字數超過限制一整個花掉,感謝您的指正,還有看到其它有問題的地方的話在麻煩不吝指教哦!!