1. 程式人生 > >linux四劍客-grep/find/sed/awk/詳解-技術流ken

linux四劍客-grep/find/sed/awk/詳解-技術流ken

1.四劍客簡介

相信接觸過linux的大家應該都學過或者聽過四劍客,即sed,grep,find,awk,有人對其望而生畏,有人對其愛不釋手。引數太多,變化形式太多,使用超級靈活,讓一部分人難以適從繼而望而生畏,淺嘗輒止即罷。有人熟練掌握,使其四劍客為己所用,在分析日誌,分析文字,統計,批量修改中游刃有餘,大大提高了工作效率。本篇博文將詳細講解四劍客的引數選項,以及使用案例,相信認真讀完本篇博文你也可以使得四劍客真正為己所用。

2.四劍客之grep

1.幾個概念

正則表示式:Regular Expression

作用:用一些特殊的字元來描述一個模式

字元:

普通字元:0-9 a-z A-Z

特殊字元

(元字元)* . {} |

正則和萬用字元

正則是用於對檔案中的內容進行過濾和匹配

萬用字元用於對檔名進行匹配

2.grep命令選項

作用:用於對檔案中的內容進行過濾

原理:逐行對檔案中的內容根據樣式進行匹配,如果匹配成功就過濾出該行

格式:grep [options] PATTERN file

PATTERN:要匹配的模式

options

-i:忽略檔案中的內容的大小寫

-o:僅僅顯示所匹配到的內容(不顯示整行)

-v:取反,用於獲取不包含指定內容的行

--color:將匹配到的內容進行著色

-A num:在匹配到指定的行以後,額外顯示下面的num

-B num:在匹配到指定的行以後,額外顯示上面的

num

-C num:在匹配到指定的行以後,額外顯示上下各num 

 3.正則表示式的特殊符號

. 表示任意一個字元
[] 表示範圍內的一個字元
[^] 表示匹配範圍以外的任意一個字元
* 表示其前面的字元出現任意次數(0,1,n)的情況(注意是匹配*前面的字元,比如*前面是5. 5*就表示匹配一個5或者0個或者n個5)
.* 表示任意長度的任意字元
? 表示其前面的字元出現最多一次的情況
\{m,n\} 表示其前面的字元出現最少m次,最多n次的情況
^ 匹配行首
$ 匹配行尾
\< 錨定單詞首部
    \> 錨定單詞尾部
\(分組\)
    \1  呼叫前面的第一個分組
    \
2 呼叫前面的第二個分組

4.擴充套件正則表示式

grep -E

egrep

擴充套件正則表示式多了一個+號和一個或者|的符號而已

5.三劍客之grep案例

例子:顯示出a.txt中不包含字母 c 的行

[[email protected] ~]# grep -v "c" a.txt

例子:統計a.txt中包含字母q的行的數量

[[email protected] ~]# grep "q" a.txt | wc -l

例子:過濾出包含大寫字母的行

[[email protected] ~]# grep "[A-Z]" a.txt

例子:匹配非數字字元

[[email protected] ~]# grep "[^0-9]" a.txt

例子:檢視包含字母a的行,要求顯示該行上下各5

[[email protected] ~]# grep --color -C 5 "a" a.txt

例子:過濾出一行中a在前,b在後的行

[[email protected] ~]#  grep --color "a.*b" b.txt

 例子:匹配ab之間有最少2c最多5c的行

[[email protected] ~]# grep "ac\{2,5\}b" a.txt

例子:過濾出以# 為開頭,且第二個字元是空格的行

[[email protected] ~]#  grep "^#[[:space:]]" a.txt

例子:過濾出行首和行位字母相同的行

[[email protected] ~]# grep "^\([a-z]\).*\1$" a.txt

例子:過濾出第一個字元是#,且第二個字串是非空字元,而且結尾是數字的行

[[email protected] ~]# grep --color "^#[^[:space:]].*[0-9]$" a.txt

3.四劍客之find

1.簡單介紹

特點:

查詢速度相對慢

準確率高,而且可以根據檔案的多種特性進行查詢

原理:

find會在指定目錄及其子目錄中進行逐級查詢

格式:

find [options] [路徑] [查詢條件] [執行的動作]

說明

路徑:就是在哪個目錄下進行查詢

可以是絕對路徑,也可以是相對路徑

 2.find的查詢條件

-name  可以使用萬用字元
-iname忽略大小寫
-groupname
-username
-gid
-uid   
-nogroup 無屬組
-nouser 無使用者
-size  檔案大小
-type 檔案型別
-mtime  建立時間
-ctime   修改時間
-atime   訪問時間
-perm  後面跟的許可權
-exec  find  xxx  -exec  命令 \;

組合條件-a,-o,-not)

3.三劍客之find案列

例子:從當前位置下找出字尾是txt的檔案和目錄

[[email protected] ~]# find ./ -name "*.txt"

例子:找檔案的屬主是 py22 的檔案和目錄

[[email protected] ~]# find / -user "py22"

例子:找檔案大小是1M的檔案

[[email protected] ~]# find / -size 1M

說明:

             查詢找結果是<=1M的檔案

    -size [+-]n

         +:大於指定的值

         -:小於指定的值

例子:找檔案大小大於1G的檔案

[[email protected] ~]# find / -size +1G

例子:找一般檔案

[[email protected] ~]# find / -type f

 例子:從/tmp下找出字尾是wps doc exel的檔案

[[email protected] ~]# ind /tmp/ -name *.doc -o -name *.exel -o -name *.wps

例子:找出系統中全部使用者都有執行的許可權的檔案

[[email protected] ~]# find / -perm -111

-perm許可權前面沒有任何符號表示精確查詢,比如查詢666,查找出來的檔案許可權必須是666許可權

-perm許可權前面有/表示模糊查詢,9個許可權包含一個即可

-perm許可權面前有-表示必須包含所指定的許可權

例子:將tmp下有執行許可權的檔案中的執行許可權去除

[[email protected] ~]#  find /tmp -perm /111 -exec chmod a-x {} \;

4.四劍客之awk

在說awk之前首先介紹幾個小命令

1.幾個小命令

cut命令

cut命令
    作用:根據指定的分隔符來切割資料,然後顯示指定的部分
    選項
        -d'字元':指定分隔符
        -f#:指定顯示分割後的那一部分資料
            輸出的情況
            1)輸出一段:指定一個編號   2
            2)輸出連續多段:編號-編號  2-5
            3)輸出不連續多段:編號,編號...  2,3,5

    # echo "bin:10:15:i am bin:/home/bin:/sbin/nologin"

    例子:輸出上面的15
    # echo "bin:10:15:i am bin:/home/bin:/sbin/nologin" | cut -d':' -f3

    例子:輸出系統中全部使用者的使用者名稱和shell型別
    # cat /etc/passwd | cut -d":" -f1,7

sort命令

sort命令
    作用:按字元進行比較和排序
    格式:sort 選項 file
    選項:
        -t:指定分隔符
        -k:根據切割後的那一段進行排序[根據切割後的那一段排序,不是取出來那一段]
        -n:表示根據數字進行排序(預設是根據字元進行排序)
        -f:忽略要比較的字元大小寫
        -u:去除重複的行(只要那個指定的欄位重複,就認定是重複的行)
        -r:按照降序排序

    例子:對檔案中的內容進行排序
    # sort mypwd
        (預設排序:針對每行的第一個字母的ASCII中的值進行比較排序)

    例子:對檔案中的內容按照冒號分割第二部分進行排序
    # sort -t":" -k2

uniq命令

uniq命令[通常結合sort先進行排序,然後再使用該命令統計相同的行出現的次數]
    作用:去除重複的行(相鄰且相同,認定為重複)
    選項:
        -c:在行首用數字表示該行出現了多少次
        -d:僅僅顯示出現過重複的行
        -u:僅僅顯示那些沒有出現重複過的行

    例子:將檔案中相同的行去重
    # sort mypwd | uniq

2.awk命令

作用:逐行處理檔案中的內容(讀取一行,處理一行)

例子:輸出使用者的uid

# cat /etc/passwd | awk -F ":" '{prin t $3}'

處理過程

1)前面的cat將內容傳遞給awk

2awk讀取一行,然後執行-F進行分割,然後執行一次{ }

格式:

awk [options] '[pattern]{action}' fileName

說明

options:選項,比如 -F 指定分隔符

pattern:輸出的條件,比如僅僅輸出以#開頭的行

action:按照選項切換,並且是符合條件的行,要執行的操作或者命令,比如輸出

概念:

記錄(record):一行就是一個記錄

分隔符(field separator):進行對記錄進行切割的時候所使用的字元

欄位(field):將一條記錄分割成的每一段

3.常用的內建變數

    FILENAME:當前處理檔案的檔名
    FS(Field Separator):欄位分隔符(預設是以空格為分隔符)
    NR(Number of Rrecord):記錄的編號(awk每讀取一行,NR就加1)
    NF(Number of Field):欄位數量(記錄了當前這條記錄包含多少個欄位)
    ORS(Output Record Separator):指定輸出記錄分隔符(指定在輸出結果中記錄末尾是什麼,預設是\n,也就是換行)[\n表示換行]
    OFS(Output Field Separator):輸出欄位分隔符
    RS:記錄分隔符

4.awk常用使用方式總結

結合本人平時使用總結可如下五種平時最常用的方式

1.結合內建變數,列印指定的幾行,以及欄位數量

例子:輸出有多餘5個欄位的行的第三個欄位

# cat a.sh | awk -F ":" 'NF>=5{print $3}'

例子:輸出每行行號和該行有幾個欄位

# cat a.sh | awk -F ":" '{print NR,NF}'

例子:輸出使用者名稱,要求所有使用者顯示在同一行,而且用空格分隔

# cat mypwd | awk 'BEGIN{FS=":"; ORS=" "}{print $1}'

2.結合正則來匹配一行或者某個欄位

例子:輸出使用者名稱以s為開頭的使用者的uid

# cat mypwd | awk -F ":" '/^s/{print $}'

例子:輸出第五個欄位是以t為結尾的使用者的姓名

# cat mypwd | awk -F ":" '$5~/t$/{print $1}'

3.採用比較符號來進行列印指定的某些行

# cat mypwd | awk 'NR>=3&&NR<=5{print NR,$1}'

# cat mypwd | awk 'NR==3,NR==5{print NR,$1}'

例子:實現僅僅輸出3 5 7行的內容,每行前面新增一個行號

# cat mypwd | awk 'NR==3||NR==5||NR==7{print NR,$1}'

4.結合BEGINEND模組統計和N++等計算某些欄位和行出現的次數

例子:統計mypwd中以#開頭的行有多少行

# cat mypwd | awk 'BEGIN{n=0}/^#/{n+=1}END{print n}'

統計:mypwd中,以:為分隔符,欄位數量在3-5的行的數目

# cat mypwd  | awk 'BEGIN{FS=":"}NF>=3&&NF<=5{n+=1}END{print n}'

5.陣列。定義一個數組採用 {ip[$3]++}END{for (i in 陣列名ipprint i,ip[i]}

例子:統計IP

[[email protected] tmp]# cat url.txt | awk -F "/+" '{urls[$2]++}END{for(key in urls)print key, urls[key]}’

5.四劍客之sed

1.簡介

文字編輯器,也是對檔案中的內容進行逐行的處理(一次處理一行)

sed的工作原理

sed讀取一行,首先將這行放入到快取中

然後,才對這行進行處理

處理完成以後,將緩衝區的內容傳送到終端

儲存sed讀取到的內容的快取區空間稱之為:模式空間(Pattern Space

格式:sed [options] file

2.選項

-p:列印輸出(會將模式空間中的內容連同處理的行的結果一併輸出)[Print 使用該選項後不要和-i一起使用,否則文字內容會被替換為只有指定的那些行
如果需要驗證的話只需要使用-p和-n進行驗證即可,不要加上-i
-n和-i也不要一起使用]
n:使用靜默模式(不輸出模式空間中的內容)[可以理解為no模式空間]-r:使用擴招正則表示式中的符號[正則regular]
-i:直接修改原始檔案(預設是修改模式空間中的檔案副本)[In place直接在檔案裡面修改]
!:對命令的執行結果取反(不顯示命令找到的內容)[和awk一樣使用單引號]&:引用前面的搜尋結果

3.操作

 a:新增
 i:插入
 d:刪除
 p:列印輸出
 s:字串替換
 c:做行替換
 r: 從一個檔案中讀取到另一個檔案中
 w: 從一個檔案中將匹配的內容寫入到另外一個檔案中

4.sed用法總結

結合本人使用,總結了如下sed常用用法

1.查詢指定的字串

例子:顯示/etc/passwd中保含root的行(顯示模式空間中的內容)

方法1set '/root/p' /etc/passwd

方法2cat /etc/passwd | sed '/root/p'

2.在指定的位置做增刪

例子:刪除以root為開頭的行

# sed '/^root/d' a.txt

例子:在包含root的行後新增一行 i am zxhk

# sed '/root/a i am zxhk' a.txt

3.按行替換

例子:將59行的內容替換為 i am zxhk

# sed '5,9c i am zxhk' a.txt

4.按照字元替換

例子:將/etc/selinux/config中的SELINUX=enforcing改成 disabled

寫法1# sed -i 's/SELINUX=disabled/SELINUX=enforcing/g' config

寫法2# sed -r -i 's/(SELINUX=)disabled/\1enforcing/g' config

5.查詢指定的內容再做替換

例子:將以r開頭的行中的oo替換為qq

# sed '/^r/{s/oo/qq/g}' passwd

6.多點編輯

例子:去除檔案中的註釋行和空白行

# grep -v -E "(^#)|(^$)" passwd.bak >passwd

# cat passwd.bak | sed -e '/^#/d' -e '/^$/d' >passwd

7.取反操作

顯示非1-3

# sed -n '1-3!p' passwd

6.結束語

四劍客已經講解完畢,熟練掌握如上常用用法,就可以在工作中游刃有餘了,試著操作一遍吧!