9.6 awk(上)
awk,支持分段匹配,awk并不会更改文件的内容,只会在屏幕上显示运行结果而已
匹配字符串的时候 必须加上"" 创建测试数据文件[root@aminglinux-02 tmp]# cp /etc/passwd ./test.txt[root@aminglinux-02 tmp]# cat test.txtroot:x:0:0:root:/root:/bin/bashbin:x:1:1:bin:/bin:/sbin/nologindaemon:x:2:2:daemon:/sbin:/sbin/nologinadm:x:3:4:adm:/var/adm:/sbin/nologinlp:x:4:7:lp:/var/spool/lpd:/sbin/nologinsync:x:5:0:sync:/sbin:/bin/syncshutdown:x:6:0:shutdown:/sbin:/sbin/shutdownhalt:x:7:0:halt:/sbin:/sbin/haltmail:x:8:12:mail:/var/spool/mail:/sbin/nologinoperator:x:11:0:operator:/root:/sbin/nologingames:x:12:100:games:/usr/games:/sbin/nologinftp:x:14:50:FTP User:/var/ftp:/sbin/nologinnobody:x:99:99:Nobody:/:/sbin/nologinsystemd-bus-proxy:x:999:997:systemd Bus Proxy:/:/sbin/nologinsystemd-network:x:192:192:systemd Network Management:/:/sbin/nologindbus:x:81:81:System message bus:/:/sbin/nologinpolkitd:x:998:996:User for polkitd:/:/sbin/nologintss:x:59:59:Account used by the trousers package to sandbox the tcsd daemon:/dev/null:/sbin/nologinpostfix:x:89:89::/var/spool/postfix:/sbin/nologinsshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologinchrony:x:997:995::/var/lib/chrony:/sbin/nologin
- 指定段的分隔符
-F ':',指定分隔符为 :,以便之后容易区分,命令是对第几段进行操作
指定 分割符为 : 冒号,打印第一段,第一段用 $1 表示
[root@aminglinux-02 tmp]# awk -F ':' '{print $1}' test.txtrootbindaemonadmlpsyncshutdownhaltmailoperatorgamesftpnobodysystemd-bus-proxysystemd-networkdbuspolkitdtsspostfixsshdchrony
打印所有段,$0 表示所有的段
awk -F ':' '{print $0}' test.txtawk '{print $0}' test.txt
-F 选项;如果没有去指定分隔符 ,那么将模式使用空白、空格为分隔符
[root@aminglinux-02 tmp]# cat 1.txt1 2aa bbdd ee[root@aminglinux-02 tmp]# awk '{print $1}' 1.txt1aadd
打印test.txt文本下的1、3、5段,因为内容太长,所以我用了head只显示10行
[root@aminglinux-02 tmp]# awk -F ':' '{print $1,$3,$5}' test.txt |headroot 0 rootbin 1 bindaemon 2 daemonadm 3 admlp 4 lpsync 5 syncshutdown 6 shutdownhalt 7 haltmail 8 mailoperator 11 operator[root@aminglinux-02 tmp]# cat -n test.txt |head 1 root:x:0:0:root:/root:/bin/bash 2 bin:x:1:1:bin:/bin:/sbin/nologin 3 daemon:x:2:2:daemon:/sbin:/sbin/nologin 4 adm:x:3:4:adm:/var/adm:/sbin/nologin 5 lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin 6 sync:x:5:0:sync:/sbin:/bin/sync 7 shutdown:x:6:0:shutdown:/sbin:/sbin/shutdown 8 halt:x:7:0:halt:/sbin:/sbin/halt 9 mail:x:8:12:mail:/var/spool/mail:/sbin/nologin 10 operator:x:11:0:operator:/root:/sbin/nologin
- 打印信息分隔
对打印出的信息,以 # 进行分隔
awk -F ':' '{print $1"#"$2"#"$3}'
[root@aminglinux-02 tmp]# awk -F ':' '{print $1"#"$2"#"$3}' test.txt |headroot#x#0bin#x#1daemon#x#2adm#x#3lp#x#4sync#x#5shutdown#x#6halt#x#7mail#x#8operator#x#11
- 关键字匹配
把包含 oo 的行,打印出来
awk '/oo/' test.txt
[root@aminglinux-02 tmp]# awk '/oo/' test.txtroot:x:0:0:root:/root:/bin/bashlp:x:4:7:lp:/var/spool/lpd:/sbin/nologinmail:x:8:12:mail:/var/spool/mail:/sbin/nologinoperator:x:11:0:operator:/root:/sbin/nologinpostfix:x:89:89::/var/spool/postfix:/sbin/nologin
匹配第一段,为oo的行,匹配的时候,支持正则,而且不需要脱义特殊符号,还支持多个条件同时匹配
awk -F ':' '$1 ~/oo/' test.txt
[root@aminglinux-02 tmp]# awk -F ':' '$1 ~/oo/' test.txtroot:x:0:0:root:/root:/bin/bash
多个关键词同时匹配,并打印出所在行的某个段
匹配root的,打印第一段、第三段信息;匹配user的打印第一段,第三段,第四段的信息[root@aminglinux-02 tmp]# awk -F ':' '/root/ {print $1,$3} /user/ {print $1,$3,$4}' test.txtroot 0operator 11tss 59 59user1 1000 1000user2 1001 1001user3 1002 1002user4 1003 1003user5 1004 1004
- 逻辑运算方式匹配关键字
awk -F ':' '$3==0' test.txt 等同于 awk -F ':' '$3==0 {print $0} ' test.txt
匹配逻辑运算方式是 $3==1000 和 $3=="1000" 是不一样的。加了双引号的数字,匹配运算方式是以 变量 LC_ALL=C 的方式进行运算,所以匹配到的结果差异很
数学运算方式匹配
[root@aminglinux-02 tmp]# awk -F ':' '$3>=1000' test.txtuser1:x:1000:1000::/home/user1:/bin/bashuser2:x:1001:1001::/home/user2:/bin/bashuser3:x:1002:1002::/home/user3:/bin/bashuser4:x:1003:1003::/home/user4:/bin/bashuser5:x:1004:1004::/home/user5:/bin/bash
逻辑运算方式匹配
[root@aminglinux-02 tmp]# awk -F ':' '$3>="1000"' test.txtdaemon:x:2:2:daemon:/sbin:/sbin/nologinadm:x:3:4:adm:/var/adm:/sbin/nologinlp:x:4:7:lp:/var/spool/lpd:/sbin/nologinsync:x:5:0:sync:/sbin:/bin/syncshutdown:x:6:0:shutdown:/sbin:/sbin/shutdownhalt:x:7:0:halt:/sbin:/sbin/haltmail:x:8:12:mail:/var/spool/mail:/sbin/nologinoperator:x:11:0:operator:/root:/sbin/nologingames:x:12:100:games:/usr/games:/sbin/nologinftp:x:14:50:FTP User:/var/ftp:/sbin/nologinnobody:x:99:99:Nobody:/:/sbin/nologinsystemd-bus-proxy:x:999:997:systemd Bus Proxy:/:/sbin/nologinsystemd-network:x:192:192:systemd Network Management:/:/sbin/nologindbus:x:81:81:System message bus:/:/sbin/nologinpolkitd:x:998:996:User for polkitd:/:/sbin/nologintss:x:59:59:Account used by the trousers package to sandbox the tcsd daemon:/dev/null:/sbin/nologinpostfix:x:89:89::/var/spool/postfix:/sbin/nologinsshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologinchrony:x:997:995::/var/lib/chrony:/sbin/nologinuser1:x:1000:1000::/home/user1:/bin/bashuser2:x:1001:1001::/home/user2:/bin/bashuser3:x:1002:1002::/home/user3:/bin/bashuser4:x:1003:1003::/home/user4:/bin/bashuser5:x:1004:1004::/home/user5:/bin/bash
- 不等于的匹配方式
test.txt文件下,第7段不等于 /sbin/nologin 的 打印整行
awk -F ':' '$7!="/sbin/nologin"' test.txt
[root@aminglinux-02 tmp]# awk -F ':' '$7!="/sbin/nologin"' test.txtroot:x:0:0:root:/root:/bin/bashsync:x:5:0:sync:/sbin:/bin/syncshutdown:x:6:0:shutdown:/sbin:/sbin/shutdownhalt:x:7:0:halt:/sbin:/sbin/haltuser1:x:1000:1000::/home/user1:/bin/bashuser2:x:1001:1001::/home/user2:/bin/bashuser3:x:1002:1002::/home/user3:/bin/bashuser4:x:1003:1003::/home/user4:/bin/bashuser5:x:1004:1004::/home/user5:/bin/bash
9.7 awk(下)
承接上一节,逻辑运算方式匹配
两个字段进行比较
awk -F ':' '$3<$4' test.txt
awk -F ':' '$3>5 && $3<7' /etc/passwd
- 判断类查找匹配 && 且
数学运算
[root@aminglinux-02 tmp]# awk -F ':' '$3>5 && $3<7' /etc/passwdshutdown:x:6:0:shutdown:/sbin:/sbin/shutdown
逻辑运算
[root@aminglinux-02 tmp]# awk -F ':' '$3>"5" && $3<"7"' /etc/passwdshutdown:x:6:0:shutdown:/sbin:/sbin/shutdowntss:x:59:59:Account used by the trousers package to sandbox the tcsd daemon:/dev/null:/sbin/nologin
|| 或
匹配第三段大于1000的 或者 第七段包含 bash
awk -F ':' '- 定义变量查找 OFS变量 OFS=# 定义 输出的时候以 # 作为分隔符
awk -F ':' '{OFS="#"} $3>1000 || $7 ~ /bash/' {print $1,$3,$7}' test.txt
[root@aminglinux-02 tmp]# awk -F ':' '{OFS="#"} $3>1000 || $7 ~ /bash/ {print $1,$3,$7}' test.txtroot#0#/bin/bashuser1#1000#/bin/bashuser2#1001#/bin/bashuser3#1002#/bin/bashuser4#1003#/bin/bashuser5#1004#/bin/bash
- 规范写法
=={OFS="#"} $3>1000 {print $1,$2,$3,$4}这一段中的 $3>1000 规范写法是 if ($3>1000)==
awk -F ':' '{OFS="#"} {if ($3>1000) {print $1,$2,$3,$4}}' test.txt 等同于 awk -F ':' '{OFS="#"} $3>1000 {print $1,$2,$3,$4}' test.txt
[root@aminglinux-02 tmp]# awk -F ':' '{OFS="#"} {if ($3>1000) {print $1,$2,$3,$4}}' test.txtuser2#x#1001#1001user3#x#1002#1002user4#x#1003#1003user5#x#1004#1004[root@aminglinux-02 tmp]# awk -F ':' '{OFS="#"} $3>1000 {print $1,$2,$3,$4}' test.txtuser2#x#1001#1001user3#x#1002#1002user4#x#1003#1003user5#x#1004#1004
NR 变量,可以作为判断条件
显示所有行的行号awk -F ':' '{print NR":"$0}' test.txt
判断用法
NR数小于等于10行,且 每行的第一段包含root 或 sync 的行awk -F ':' 'NR<=10 && $1 ~ /root|sync/' test.txt
[root@aminglinux-02 tmp]# awk -F ':' 'NR<=10 && $1 ~ /root|sync/' test.txtrootx:0:0:root:/root:/bin/bashsync:x:5:0:sync:/sbin:/bin/sync
NF 变量,可以作为判断条件
显示所有行的段数awk -F ':' '{print NF":"$0}' test.txt
[root@aminglinux-02 tmp]# awk -F ':' '{print NF":"$0}' test.txt6:rootx:0:0:root:/root:/bin/bash7:bin:x:1:1:bin:/bin:/sbin/nologin7:daemon:x:2:2:daemon:/sbin:/sbin/nologin7:adm:x:3:4:adm:/var/adm:/sbin/nologin7:lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin7:sync:x:5:0:sync:/sbin:/bin/sync7:shutdown:x:6:0:shutdown:/sbin:/sbin/shutdown7:halt:x:7:0:halt:/sbin:/sbin/halt7:mail:x:8:12:mail:/var/spool/mail:/sbin/nologin7:operator:x:11:0:operator:/root:/sbin/nologin7:games:x:12:100:games:/usr/games:/sbin/nologin7:ftp:x:14:50:FTP User:/var/ftp:/sbin/nologin7:nobody:x:99:99:Nobody:/:/sbin/nologin7:systemd-bus-proxy:x:999:997:systemd Bus Proxy:/:/sbin/nologin7:systemd-network:x:192:192:systemd Network Management:/:/sbin/nologin7:dbus:x:81:81:System message bus:/:/sbin/nologin7:polkitd:x:998:996:User for polkitd:/:/sbin/nologin7:tss:x:59:59:Account used by the trousers package to sandbox the tcsd daemon:/dev/null:/sbin/nologin7:postfix:x:89:89::/var/spool/postfix:/sbin/nologin7:sshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologin7:chrony:x:997:995::/var/lib/chrony:/sbin/nologin7:user1:x:1000:1000::/home/user1:/bin/bash7:user2:x:1001:1001::/home/user2:/bin/bash7:user3:x:1002:1002::/home/user3:/bin/bash7:user4:x:1003:1003::/home/user4:/bin/bash7:user5:x:1004:1004::/home/user5:/bin/bash
- 判断用法 NF等于6段,且 每行的第一段包含root 或 sync 的行
awk -F ':' 'NF==6 && $1 ~ /root|sync/' test.txt
[root@aminglinux-02 tmp]# awk -F ':' 'NF==6 && $1 ~ /root|sync/' test.txtrootx:0:0:root:/root:/bin/bash
- 赋值 显示/etc/passwd 的前三行,把运行结果丢给awk,awk 对之前的结果 实行 对前三的第一段赋值为 root
head -n 3 /etc/passwd |awk -F ':' '$1="root"'
[root@aminglinux-02 tmp]# head -n 3 /etc/passwd |awk -F ':' '$1="root"'root x 0 0 root /root /bin/bashroot x 1 1 bin /bin /sbin/nologinroot x 2 2 daemon /sbin /sbin/nologin
- 求值
tot为一个值,运算的时候是循环运算的,但是中间加了一个 END 表示运算结束,然后打印出tot的值;tot值初始为0,一次运算加上第三段的值以后开始变化,一直到END结束
下面这条命令,就是求test.txt 文件里面 第三段的和值awk -F ':' '{(tot=tot+$3)}; END {print tot}' test.txt