AWK简单入门
简介
awk是一种编程语言,其名称得自于它的创始人 Alfred Aho 、Peter Weinberger 和 Brian Kernighan 姓氏的首个字母 ,用于在linux/unix下对文本和数据进行处理。grep,sed,awk被称为linux中的‘‘三剑客’
grep 更适合单纯的查找或匹配文本
sed 更适合编辑匹配到的文本
awk 更适合格式化文本,对文本进行较复杂格式处理
简单使用
-
首先通过nestat命令列出开放的端口,并写入到文件
netstat -tunlp > netstat.txt //文件内容如下 Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name tcp 0 0 0.0.0.0:3306 0.0.0.0:* LISTEN - tcp 0 0 0.0.0.0:21 0.0.0.0:* LISTEN - tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN - tcp 0 0 127.0.0.1:631 0.0.0.0:* LISTEN - tcp 0 0 127.0.0.1:6011 0.0.0.0:* LISTEN - tcp 0 0 :::22 :::* LISTEN - tcp 0 0 ::1:631 :::* LISTEN - tcp 0 0 ::1:6011 :::* LISTEN - udp 0 0 0.0.0.0:631 0.0.0.0:* -
-
可以看到文件结构是10行7列,通过awk我们可以很方便的把第一列和第四列打印出来
awk '{print $1,$4}' netstat.txt //执行命令结果 Proto Local tcp 0.0.0.0:3306 tcp 0.0.0.0:21 tcp 0.0.0.0:22 tcp 127.0.0.1:631 tcp 127.0.0.1:6011 tcp :::22 tcp ::1:631 tcp ::1:6011 udp 0.0.0.0:631
命令详解
-
语法
awk options 'pattern {action }' input-file > output-file pattern 表示匹配规则,action表示动作,action一般为打印print example: awk '{print $1,$4}' netstat.txt awk -F: '{print $1,$4}' netstat.txt // -F 表示指定分割符为:,默认是空格或tab awk '/tcp/ {print $1,$4}' netstat.txt // 打印出包含字符tcp的行
-
内建变量
变量 描述 $0 当前记录(这个变量中存放着整个行的内容) 1 1~ 1 n 当前记录的第n个字段,字段间由FS分隔 FS 输入字段分隔符 默认是空格或Tab,FS是field separator的缩写 NF 当前记录中的字段个数,就是有多少列,number of field的索写 NR 已经读出的记录数,就是行号,从1开始,如果有多个文件话,这个值也是不断累加中。nubmer of record的缩写 FNR 当前记录数,与NR不同的是,这个值会是各个文件自己的行号 RS 输入的记录分隔符, 默认为换行符,record separator的缩写 OFS 输出字段分隔符, 默认也是空格 output field separator的缩写 ORS 输出的记录分隔符,默认为换行符 output record separator的缩写 FILENAME 当前输入文件的名字 -
如何使用
-
打印出有7个字段的列
awk '{NF==7} {print}' netstat.txt
-
打印总共有几条记录
awk 'END{print NR}' netstat.txt
-
带行号输出内容
awk '{print NR,$0}' netstat.txt
-
冒号为字段分隔符,打印出行数,第一列内容,字段数和字段分隔符
awk -F: '{print NR,$1,"NF="NF,"FS="FS}' /etc/passwd 原内容 root:x:0:0:root:/root:/bin/bash 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 执行命令之后 1 root NF=7 FS=: 2 bin NF=7 FS=: 3 daemon NF=7 FS=: 4 adm NF=7 FS=: 5 lp NF=7 FS=: 6 sync NF=7 FS=: 7 shutdown NF=7 FS=
-
通过指定输出的分隔符为逗号,可以导出csv文件
awk 'BEGIN{FS=":";OFS=","} {print $1,$2,$3,$4,$5,$6,$7}' /etc/passwd > passwd.csv
-
-
BEGIN 和 END
-
awk的通常格式为
awk 'BEGIN{最开始执行,只执行一次} {在begin之后执行,每一行都会执行一次} END{最后执行,只执行一次}
-
例子
新建一个文件myscript,写入下面的脚本
BEGIN { print "Users and thier corresponding home" print " UserName \t HomePath" print "___________ \t __________" FS=":" } { print $1 " \t " $6 } END { print "The end" }
通过-f 指定awk脚本
awk -f myscript /etc/passwd 结果为 Users and thier corresponding home UserName HomePath ___________ __________ root /root bin /bin daemon /sbin adm /var/adm lp /var/spool/lpd sync /sbin shutdown /sbin halt /sbin The end
高级用法
-
字符串匹配
# //是模式,表示这是一个正则表达式的匹配 awk '/LISTEN/' netstat.txt ## 格式为 exp ~/regexp/ 表示匹配第一个字段中有udp的记录 awk '$1 ~ /udp/' netstat.txt ## 格式为 exp !~/regexp/ 表示匹配第一个字段中没有udp的记录 awk '$1 !~/udp/' netstat.txt #exp ~/regexp和exp !~/regexp/可以用在if,while,for,do中做判断条件 awk '{ if ($1 ~ /udp/) print }' netstat.txt awk '{ if ($1 !~ /udp/) print }' netstat.txt
-
内置函数
awk中可以使用shell中的内置函数
# 输出字段的长度 awk '{print $1 " length is " length($1)}' netstat.txt tcp length is 3 tcp length is 3 tcp length is 3 tcp length is 3 tcp length is 3 tcp length is 3 tcp length is 3 tcp length is 3 # 转成大写 awk '{print $1 " upper is " toupper($1)}' netstat.txt tcp upper is TCP tcp upper is TCP tcp upper is TCP tcp upper is TCP tcp upper is TCP tcp upper is TCP tcp upper is TCP tcp upper is TCP udp upper is UDP
参考资料
-