AWK
linux中文本处理三剑客之一,其他两个分别为grep,sed
awk:是个报告生成器,也是文本处理工具。从文本中抽取符合条件的数据并以特定的格式显示出来。
linux中的AWK,GNU-awk就是gawk,是扩展了的awk
语法:
awk [option] 'PATTERN{ACTION}' file1 file2.......
PATTERN:是指定的抽取文件数据的条件
ACTION:要对匹配的数据进行的处理动作
可同时处理多个文件
awk读取数据时,把每行当作一条记录,每条记录可以细分为字段,默认以空格分字段,也可以自定义划分字段。
[root@localhost ~]# echo "hello boys hello girls">t1 [root@localhost ~]# awk '{print $1,$3}' t1 # $1,$3分别代表第一,第三个字段 hello hello [root@localhost ~]# awk '{print $0}' t1 # $0 代表整条记录 hello boys hello girls
-F:指定输入分隔符 输入指的是输入的数据
[root@localhost ~]# awk -F: '{print $1,$3,$4}' /etc/passwd # 指定的分隔符: root 0 0 bin 1 1 daemon 2 2 ...
OFS:awk的内置变量,表示输出分隔符 (默认的输出分隔符为空格,可以修改)
[root@localhost ~]# awk 'BEGIN{OFS="@"}{print $1,$3,$4}' t1 hello@hello@girls
awk的输出:
1、print
print $1,$2,$3
awk的变量:
内置变量:
FS:field separator 读取文本时,所使用的分隔符,与-F一样
root@localhost ~]# awk 'BEGIN{FS=":"}{print $1,$3,$4}' /etc/passwd root 0 0 bin 1 1 daemon 2 2 ...
RS:record separator 输入文本信息所使用的行分隔符(用的比较少)
OFS:output field separator 输出分隔符(见上)
ORS:output row separator 输出信息所使用的行分隔符
awk -F: 'BEGIN{ORS="<==>"}{print $1,$3,$4}' /etc/passwd root 0 0<==>bin 1 1<==>daemon 2 2<==>adm 3 4<==>lp 4 7<==>sync 5 0<==>shutdown 6 0<==>ha ...
NR:awk所处理的记录数;如果有多个文件,这个数目会吧处理的多个文件中的行统一记数
[root@localhost ~]# awk '{print NR}' t 1 2 3 4 [root@localhost ~]# awk '{print NR}' t1 1 [root@localhost ~]# awk '{print NR}' t1 t 1 2 3 4 5
注意$NR ,NR只是代表记录数(行数),$NR代表第几个字段,有时用得到
FNR:与NR不同的是,FNR用于记录正在处理的行是当前这一个文件中的行数
[root@localhost ~]# awk '{print FNR}' t t1 1 2 3 4 1
NF:当前记录的字段的个数 field,用的较多
[root@localhost ~]# awk '{print NF}' t 1 2 3 2 [root@localhost ~]# awk '{print $NF}' t # 打印每行的最后一个字段 helloworld sd sa y
用户自定义变量:
gawk里变量名区分大小写,变量的定义规范与多数编创语言一样
1.在脚本内赋值变量:
[root@localhost ~]# awk '{var="hello world";print var}' hello world # 后面没接文件,按一次回车,执行输出一次自定义变量var hello world [root@localhost ~]# awk 'BEGIN{var="hello world";print var}' hello world # 加了BEGIN 只输出一次,BEGIN的作用是让紧跟着的操作在第一条记录之前执行一次 [root@localhost ~]#
2.在命令行内赋值变量:
[root@localhost ~]# awk -v var="hello world" '{print var}' hello world hello world
AWK的输出:
printf
默认不会打印换行\n
%c:显示字符的ASCII码
%d %i:十进制整数
%e %E:科学计数法
%f:显示浮点数
%s:显示字符串
%u:无符号整数
%%:显示%本身
修饰符:
N:显示的宽度
-:左对齐,默认是右对齐
+:显示数值符号
右对齐输出系统中每个用户的UID
[root@localhost ~]# awk -F: '{printf "%5d\n",$3}' /etc/passwd 0 1 ...
AWK的操作符:
算术操作符:
-X:负数
x^y:x的y次方
x**y:
x*y:乘法
x/y:
x+y
x-y
x%y:取余
数值操作符:
=:赋值
+=:
-=:
*=
/=
%=
^=
**=
++
--
布尔值:
x<y:
x<=y
x>y
x>=y
x==y
x!=y
x~y:X是个字符串,Y是个匹配模式,若X被Y匹配到则为真 x~/^r/
x!~y:
表达式之间的逻辑关系:
&&
||
!
条件表达式:
A=4
B=3
A>B? a is max:b is max
AWK模式:
awk 'PATTERN{ACTION}' file file1 file2....
常见的模式:
1、regexp 正则表达式,格式为/regular expression/
[root@localhost ~]# awk -F: '/^r/{print $1}' /etc/passwd # 输出以r开头的行的第一个字段 root
2、表达式:其值非0或者为非空字符的时候满足条件,
[root@localhost ~]# awk -F: '$3>=500{print $1,$3}' /etc/passwd tom 500
[root@localhost ~]# awk -F: '$7~/bash$/{print $1,$7}' /etc/passwd root /bin/bash
3、ranges:指定范围 模式1,模式2
从第一次匹配到的模式1开始到第一次匹配到模式2为止(闭区间)
[root@localhost ~]# awk -F: '$3==0,$7~/shutdown$/{print $1,$3,$7}' /etc/passwd root 0 /bin/bash bin 1 /sbin/nologin daemon 2 /sbin/nologin adm 3 /sbin/nologin lp 4 /sbin/nologin sync 5 /bin/sync shutdown 6 /sbin/shutdown [root@localhost ~]#
4、BEGIN/END:这是个特殊模式,仅在AWK命令执行前运行一次或者结束前运行一次
BEGIN:在awk执行前运行一次
END:在结束前运行一次
注意:与BEGIN,END关联的操作只执行一次
[root@localhost ~]# awk -F: 'BEGIN{printf"%10s%6s%15s\n","USERNAME","UID","SHELL"}$3==0,$7~/shutdown$/{printf "%10s%6d%15s\n",$1,$3,$7}END{print "End of report"}' /etc/passwd USERNAME UID SHELL root 0 /bin/bash bin 1 /sbin/nologin daemon 2 /sbin/nologin adm 3 /sbin/nologin lp 4 /sbin/nologin sync 5 /bin/sync shutdown 6 /sbin/shutdown End of report
5、空模式(没有匹配条件,来什么处理什么)
[root@localhost ~]# awk -F: '{print $1}' /etc/passwd root bin daemon adm lp sync shutdown ...