Linux基礎(chǔ)之三劍客AWK進階

  • 上篇已經(jīng)講了AWK基礎(chǔ)篇
  • 這篇開始講進階

awk工作原理

  • 一次讀取一行文本,按輸入分隔符進行切片,切成多個組成部分,將每片直接保存在內(nèi)建的變量中,1,2,3….,引用指定的變量,可以顯示指定斷,或者多個斷。如果需要顯示全部的,需要使用0來引用
  • 可以對單個片斷進行判斷,也可以對所有斷進行循環(huán)判斷
  • 其默認分隔符為空格

awk PATTERN

  • PATTERN:根據(jù)pattern條件,過濾匹配的行,再做處理
  • 格式 awk [option] 'pattern{action}' file
  • 那什么是PATTERN
  • 如果有一個文件 ,這個文件每讀入一行,PATTERN就會根據(jù)條件做過濾處理
  • 如正則表達式,如果符合條件他就會進入action進去處理
  • 如果不符合他就不管他,接著讀取另外一行,以此類推

不過PATTERN有多種寫法

 - 如果為指定:空模式,匹配每一行 ,意思就是說不寫PATTERN,只寫action
 - 示例
     [root@localhost ~]# awk -F: '{print $1,3}' /etc/passwd
root 3
bin 3
daemon 3
adm 3
lp 3
sync 3
shutdown 3
halt 3
mail 3
operator 3
games 3
ftp 3
nobody 3
systemd-bus-proxy 3
systemd-network 3
dbus 3
polkitd 3
colord 3
abrt 3
  • 我沒有寫PATTERN,所以他會對所有行的第一和第三行打印出來,這就是空模式,匹配每行

  • 正則表達式的限定,/regular expression/:僅處理能夠模式匹配到的行,需要用/ /括起來

  • 示例

[root@localhost ~]# awk  /^UUID/ /etc/fstab 
UUID=5fa28b49-456d-4303-81d0-811b1bfa3ae9 /                       xfs     defaults        0 0
UUID=b0e8912e-cb67-4973-8557-f190f961c0cd /boot                   xfs     defaults        0 0
UUID=c204831a-efc0-4b13-bc39-259bd22cb677 /usr                    xfs     defaults        0 0
UUID=c8298654-edd5-44df-8014-1dbf1fb8dba7 swap                    swap    defaults        0 0
  • 我沒有填寫print 那是因為默認自動打印$0,就算我寫了也一樣,想取什么,就取什么
[root@localhost ~]# awk  '/^UUID/ {print $0  }' /etc/fstab 
UUID=5fa28b49-456d-4303-81d0-811b1bfa3ae9 /                       xfs     defaults        0 0
UUID=b0e8912e-cb67-4973-8557-f190f961c0cd /boot                   xfs     defaults        0 0
UUID=c204831a-efc0-4b13-bc39-259bd22cb677 /usr                    xfs     defaults        0 0
UUID=c8298654-edd5-44df-8014-1dbf1fb8dba7 swap                    swap    defaults        0 0
  • 還可以取反哦
    [root@localhost ~]# awk '!/^UUID/ {print $0 }' /etc/fstab
#
# /etc/fstab
# Created by anaconda on Thu Jul 13 08:26:25 2017
#
# Accessible filesystems, by reference, are maintained under '/dev/disk'
# See man pages fstab(5), findfs(8), mount(8) and/or blkid(8) for more info
#
  • 甚至我還可以拿他來取磁盤分區(qū)使用列表哦
[root@localhost ~]# df| awk '/^\/dev\/sd/ {print $5}'
1%
13%
30%
  • relational expression: 關(guān)系表達式,結(jié)果為“真”才會被處理
  • 真:結(jié)果為非0值,非空字符串
  • 假:結(jié)果為空字符串或0值
  • 意思就是只要不是為0都打印,為0就不打印
  • 示例
[root@localhost ~]# awk -F: '"" {print $0  }' /etc/fstab  
  • 沒打印如果給他個任意字符串
[root@localhost ~]# awk -F: '"rrr" {print $0  }' /etc/fstab 

#
# /etc/fstab
# Created by anaconda on Thu Jul 13 08:26:25 2017
#
# Accessible filesystems, by reference, are maintained under '/dev/disk'
# See man pages fstab(5), findfs(8), mount(8) and/or blkid(8) for more info
#
UUID=5fa28b49-456d-4303-81d0-811b1bfa3ae9 /                       xfs     defaults        0 0
UUID=b0e8912e-cb67-4973-8557-f190f961c0cd /boot                   xfs     defaults        0 0
UUID=c204831a-efc0-4b13-bc39-259bd22cb677 /usr                    xfs     defaults        0 0
UUID=c8298654-edd5-44df-8014-1dbf1fb8dba7 swap                    swap    defaults        0 0

line ranges:行范圍

  • startline,endline:/pat1/,/pat2/ 不支持直接給出數(shù)字格式
  • 示例
[root@localhost ~]# awk -F: '/^b/,/^f/' /etc/passwd
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin
sync:x:5:0:sync:/sbin:/bin/sync
shutdown:x:6:0:shutdown:/sbin:/sbin/shutdown
halt:x:7:0:halt:/sbin:/sbin/halt
mail:x:8:12:mail:/var/spool/mail:/sbin/nologin
operator:x:11:0:operator:/root:/sbin/nologin
games:x:12:100:games:/usr/games:/sbin/nologin
ftp:x:14:50:FTP User:/var/ftp:/sbin/nologin

-還可以取中間

[root@localhost ~]# awk -F: 'NR>=10&&NR<=20{print NR,$0}'  /etc/passwd  
10 operator:x:11:0:operator:/root:/sbin/nologin
11 games:x:12:100:games:/usr/games:/sbin/nologin
12 ftp:x:14:50:FTP User:/var/ftp:/sbin/nologin
13 nobody:x:99:99:Nobody:/:/sbin/nologin
14 systemd-bus-proxy:x:999:997:systemd Bus Proxy:/:/sbin/nologin
15 systemd-network:x:192:192:systemd Network Management:/:/sbin/nologin
16 dbus:x:81:81:System message bus:/:/sbin/nologin
17 polkitd:x:998:996:User for polkitd:/:/sbin/nologin
18 tss:x:59:59:Account used by the trousers package to sandbox the tcsd daemon:/dev/null:/sbin/nologin
19 postfix:x:89:89::/var/spool/postfix:/sbin/nologin
20 sshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologin

BEGIN/END模式

  • 通常,對于每個輸入行,awk 都會執(zhí)行每個腳本代碼塊一次。然而,在許多編程情況中
  • 可能需要在awk 開始處理輸入文件中的文本之前執(zhí)行初始化代碼。對于這種情況,awk 允許
  • 您定義一個BEGIN 塊。我們在前一個示例中使用了BEGIN 塊。因為awk 在開始處理輸入文件之前會執(zhí)行BEGIN 塊
  • 因此它是初始化 FS(字段分隔符)變量、打印頁眉或初始化其它
  • 在程序中以后會引用的全局變量的極佳位置
  • 比如我打表頭
[root@localhost ~]# awk -F: 'BEGIN{print" linenumber     username    userid"}NR>=10&&NR<=20{printf  "%s-12   %+15s %+10d \n " ,NR,$1,$3}'  /etc/passwd
 linenumber     username    userid
10-12          operator        +11 
 11-12             games        +12 
 12-12               ftp        +14 
 13-12            nobody        +99 
 14-12   systemd-bus-proxy       +999 
 15-12   systemd-network       +192 
 16-12              dbus        +81 
 17-12           polkitd       +998 
 18-12               tss        +59 
 19-12           postfix        +89 
 20-12              sshd        +74 

awk action,循環(huán),數(shù)組

  • 常用的action分類
  • Expressions:算術(shù),比較表達式等
  • Control statements:if, while等
  • Compound statements:組合語句
  • input statements
  • output statements:print等

awk控制語句if-else

  • 語法:if(condition){statement;…}[else statement]:簡單語句,如果條件成立就執(zhí)行語句,如果不成立我就執(zhí)行else后面的語句
  • if(condition1){statement1}else if(condition2){statement2}:復(fù)雜語句,如果條件成立我就執(zhí)行后面的語句,如果不成立我會檢測后面的語句成立不成立,如果還不成立我就執(zhí)行后面的else后面的語句
  • else{statement3}
  • 使用場景:對awk取得的整行或某個字段做條件判斷,if,else可以寫多個,和bash不同
  • 示例
  • 第一判斷
[root@localhost ~]# awk -F: '{if($NF=="/bin/bash") print $1}' /etc/passwd
root

-第二判斷

[root@localhost ~]# awk '{if(NF>5) print $0}' /etc/fstab
# Created by anaconda on Fri Jul 14 03:57:39 2017
# Accessible filesystems, by reference, are maintained under '/dev/disk'
# See man pages fstab(5), findfs(8), mount(8) and/or blkid(8) for more info
/dev/mapper/cl-root     /                       xfs     defaults        0 0
/dev/mapper/cl-app      /app                    xfs     defaults        0 0
UUID=c15af5a4-49d5-4551-abda-921540bf8424 /boot                   xfs     defaults        0 0
/dev/mapper/cl-swap     swap                    swap    defaults        0 0
  • 第三判斷
[root@localhost ~]# df -h|awk -F% '/^\/dev/{print $1}'|awk '$NF>=10{print $1,$5}' 
/dev/sda1 14

awk控制語句

  • while循環(huán)
  • 語法:while(condition){statement;…}
  • 條件“真”,進入循環(huán);條件“假”,退出循環(huán)
  • 使用場景:
  • 對一行內(nèi)的多個字段逐一類似處理時使用
  • 對數(shù)組中的各元素逐一處理時使用
  • while是處理字段的,要記住哦
  • 行循環(huán)AWK自帶
  • awk 提供了非常好的類似于 C 語言的if 語句。
{ 
 if ( $1== "foo" ) { 
 if ( $2== "foo" ) { 
 print "uno" 
 } else { 
 print "one" 
 } 
 } elseif ($1== "bar" ) { 
 print "two" 
 } else { 
 print "three" 
 } 
} 
  • 示例一
[root@localhost ~]# awk '/^[[:space:]]*linux16/{i=1;while(i<=NF) {print $i,length($i); i++}}' /etc/grub2.cfg
linux16 7
/vmlinuz-3.10.0-514.el7.x86_64 30
root=/dev/mapper/cl-root 24
ro 2
crashkernel=auto 16
rd.lvm.lv=cl/root 17
rd.lvm.lv=cl/swap 17
rhgb 4
quiet 5
LANG=en_US.UTF-8 16
net.ifnames=0 13
linux16 7
/vmlinuz-0-rescue-a8151f75d28c4b7ba1db0b5ad8c60cd6 50
root=/dev/mapper/cl-root 24
ro 2
crashkernel=auto 16
rd.lvm.lv=cl/root 17
rd.lvm.lv=cl/swap 17
rhgb 4
quiet 5
  • 示例二
[root@localhost ~]# awk '/^[[:space:]]*linux16/{i=1;while(i<=NF) {if(length($i)>=10) {print $i,length($i)}; i++}}' /etc/grub2.cfg
/vmlinuz-3.10.0-514.el7.x86_64 30
root=/dev/mapper/cl-root 24
crashkernel=auto 16
rd.lvm.lv=cl/root 17
rd.lvm.lv=cl/swap 17
LANG=en_US.UTF-8 16
net.ifnames=0 13
/vmlinuz-0-rescue-a8151f75d28c4b7ba1db0b5ad8c60cd6 50
root=/dev/mapper/cl-root 24
crashkernel=auto 16
rd.lvm.lv=cl/root 17
rd.lvm.lv=cl/swap 17
  • do-while循環(huán)
  • 語法:do {statement;…}while(condition
  • 意義:無論真假,至少執(zhí)行一次循環(huán)體
  • 示例
[root@localhost ~]#  awk 'BEGIN{ total=0;i=0;do{ total+=i;i++;}while(i<=100);print total}'
5050

for循環(huán)

  • for循環(huán)
  • 語法:for(expr1;expr2;expr3) {statement
  • 常見用法:
  • for(variable assignment;condition;iteration
  • {for-body}
  • 特殊用法:能夠遍歷數(shù)組中的元素
  • 語法:for(var in array) {for-body}
  • 示例
[root@localhost ~]# awk '/^[[:space:]]*linux16/{for(i=1;i<=NF;i++) {print $i,length($i)}}' /etc/grub2.cfg
linux16 7
/vmlinuz-3.10.0-514.el7.x86_64 30
root=/dev/mapper/cl-root 24
ro 2
crashkernel=auto 16
rd.lvm.lv=cl/root 17
rd.lvm.lv=cl/swap 17
rhgb 4
quiet 5
LANG=en_US.UTF-8 16
net.ifnames=0 13
linux16 7
/vmlinuz-0-rescue-a8151f75d28c4b7ba1db0b5ad8c60cd6 50
root=/dev/mapper/cl-root 24
ro 2
crashkernel=auto 16
rd.lvm.lv=cl/root 17
rd.lvm.lv=cl/swap 17
rhgb 4
quiet 5

其他語句

  • switch語句
  • 語法:switch(expression) {case VALUE1 or /REGEXP/:
  • statement1; case VALUE2 or /REGEXP2/: statement2;
  • break和continue
  • awk ‘BEGIN{sum=0;for(i=1;i<=100;i++)
  • {if(i%2==0)continue;sum+=i}print sum}‘
  • awk ‘BEGIN{sum=0;for(i=1;i<=100;i++)
  • {if(i==66)break;sum+=i}print sum}‘
  • 示例
[root@localhost ~]# awk -F: '{if($3%2!=0) next; print $1,$3}' /etc/passwd
root 0
daemon 2
lp 4
shutdown 6
mail 8
games 12
ftp 14
systemd-network 192
polkitd 998
libstoragemgmt 996
rpc 32
rtkit 172
geoclue 994
gdm 42
nfsnobody 65534
ntp 38
sshd 74
tcpdump 72
mageedu 1000

AWK數(shù)組

  • 關(guān)聯(lián)數(shù)組:array[index-expression]
  • index-expression:
  • 可使用任意字符串;字符串要使用雙引號括起來
  • 如果某數(shù)組元素事先不存在,在引用時,awk會自動創(chuàng)建此元素,并將其值初始化為“空串”
  • 若要判斷數(shù)組中是否存在某元素,要使用“index in array”格式進行遍歷
  • 示例一
  • 數(shù)組非常繞好好看
[root@localhost ~]# awk 'BEGIN{weekdays["mon"]="Monday";weekdays["tue"]="Tuesday";print weekdays["mon"]}'
Monday
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 轉(zhuǎn)載 原文的排版和內(nèi)容都更加友好,并且詳細,我只是在這里貼出了一部分留作自己以后參考和學(xué)習(xí),如希望更詳細了解AWK...
    XKirk閱讀 3,362評論 2 25
  • 本章主要學(xué)習(xí)內(nèi)容awk介紹 ?awk基本用法 ?awk變量 ?awk格式化 ?awk操作符 ?awk條件判斷 ?a...
    楠人幫閱讀 1,368評論 0 8
  • awk:報告生成器,格式化文本輸出 內(nèi)容: awk介紹 awk基本用法 awk變量 awk格式化 awk操作符 a...
    BossHuang閱讀 1,551評論 0 9
  • awk介紹awk變量printf命令:實現(xiàn)格式化輸出操作符awk patternawk actionawk數(shù)組aw...
    哈嘍別樣閱讀 1,731評論 0 4
  • awk: grep,sed,awk grep:文本過濾 sed:文本編輯 awk:文本格式化工具; 1 什么是aw...
    木林森閱讀 1,895評論 0 16

友情鏈接更多精彩內(nèi)容