之前给大家讲述了文本处理三剑客前两种,grep和sed。但是这周学习了第三种awk,感觉awk比前两个功能还要强大,相比sed也是以行进行处理,但是awk能以每一行的间隔符进行处理,用起来会更加方便。因此决定这周给大家详细介绍介绍awk。
awk的基本用法:awk [options] ‘pattern{action statements;..}’ filename
一、options
-F 指定间隔符
-v 指定变量
FS:输入字段分隔符,默认为空白字符
OFS:输出字段分隔符,默认为空白字符
RS:输入记录分隔符,指定输入时的换行符,原换行符仍有效
ORS:输出记录分隔符,输出时用指定符代替换行符
变量:NF:字段数量
NR:行号
FNR:各文件分别计数,行号
FILENAME:当前文件名
ARGC:命令行参数的个数
ARGV:数组,保存的是命令行所给定的各参数
还能自己定义变量:-v var=“定义变量”,在后面引用时候不用加$
-f:调用文件内容
二、pattern
BEGIN{头部信息}{print} 自己定义头部信息有BEGIN可以后面不用带文件
END{} 在awk从输入中读取完所有的行之后即被执行
// 还可以用正则匹配行
(1)如果未指定:空模式,匹配每一行
(2) /regular expression/:仅处理能够模式匹配到的行,需要用/ /括起来
(3) relational expression: 关系表达式,结果为“真”才会被处理
真:结果为非0值,非空字符串
假:结果为空字符串或0值
(4) line ranges:行范围 startline,endline:/pat1/,/pat2/ 不支持直接给出数字格式
例子:打印/etc/passwd/奇数行和偶数行
打印奇数行:
打印偶数行:
三、print
printf “FORMAT”, item1, item2, ...
特点:(1) 必须指定FORMAT
(2) 不会自动换行,需要显式给出换行控制符,\n
(3) FORMAT中需要分别为后面每个item指定格式符
格式符:%c: 显示字符的ASCII码
%d, %i: 显示十进制整数
%e, %E:显示科学计数法数值
%f:显示为浮点数
%g, %G:以科学计数法或浮点形式显示数值
%s:显示字符串
%u:无符号整数
%%: 显示%自身
修饰符:#[.#]:第一个数字控制显示的宽度;第二个#表示小数点后精度,%3.1f
-: 左对齐(默认右对齐) %-15s
+:显示数值的正负符号 %+d
例如:取出/etc/passwd的第一列和第三列,第一列左对齐,第三列取3个小数点
printf 里面有几个%号,就对应后面有几个变量,切数据是一一对应的
四、操作符
算术操作符:
x+y, x-y, x*y, x/y, x^y, x%y
-x: 转换为负数
+x: 转换为数值
字符串操作符:没有符号的操作符,字符串连接
赋值操作符:
=, +=, -=, *=, /=, %=, ^= ++, --
比较操作符: = =, !=, >, >=, <, <=
模式匹配符:
~:左边是否和右边匹配包含
!~:是否不匹配
例如:检测磁盘使用率是否超过百分之十
逻辑操作符:&& ||
&&在awk中表示切的意思,不是bash的短路与
||在awk中表示或的意思,不是bash的短路非
例子:取/etc/passwd里卖的4—9行
条件表达式(三目表达式):
selector?if-true-expression:if-false-expression
如果selector为真就执行?后面的,如果为假就执行:后面的
五、 action
(1)if的用法:if(判断语句){命令}[else 命令]
如果只是一条命令,就不需要加{}了
使用场景:对awk取得的整行或者某个字段做条件判断
例如:统计日志里面访问IP地址最多的直接禁用。但是bash里面的命令不能直接在awk里面用,如果想用需要加入system("hostname")
(2)while的用法:while(判断语句){循环体}
使用场景:对一行内的多个字段逐一类似处理时使用
对数组中的各元素逐一处理时使用
例子:显示/etc/passwd下的以:为间隔符,每个字段的字节数
(3)do-while的用法:do{循环体}while(判断语句)
意义:无论真假,至少执行一次循环体
例子:计算前100的和
(4)for的用法:for(expr1;expr2;expr3){命令}
特殊的用法:for(var in array) {for-body}
例子:算出/etc/grub2.cfg中带linux16的行每个字符串多少个
(5)break和continue的用法
例子:奇数和
例子:从1加到100,如果等于66就退出循环
(6)next的用法
提前结束对本行处理而直接进入下一行处理
六、awk数组(默认用的是关联数组)
(1)可使用任意字符串;字符串要使用双引号括起来
(2)如果某书元素事先不存在,在引用时,awk会自动创建此元素,并将其值初始化为“空串”
若要判断数组中是否存在某元素,要使用“index in array”格式进行遍历
for遍历数组 for(i in title){print i title[i]}
七、awk函数
1、rand生成随机数
int 对数字取整
例如:取出1-50随机数
bash中:echo $[RANDOM%50+1]
2、length([s]):返回指定字符串的长度
3、sub(r,s,[t]):对t字符串进行搜索r表示的模式匹配的内容,并将第一个匹配的内容替换为s
4、gsub(r,s,[t]):对t字符串进行搜索r表示的模式匹配的内容,并全部替换为s所表示的内容
例如:
5、split(s,array,[r]):以r为分隔符,切割字符串s,并将切割后的结果保存至array所表示的数组中,第一个索引值为1,第二个索引值为2,.....
例子:统计IP地址重复的次数
6、可以自己定义函
格式:function name(虚拟参数1,虚拟参数2,...){
命令行
return expression(返回一个具体的值)
}
看完以上awk的用法是不是感觉跟bash用法大同小异,所以在文本处理三剑客中感觉awk用处相对于前两个用法更广。