三剑客"老大"awk,教程超级详细,看完就能get!
目录
Linux 三剑客之awk
简介
应用场景
awk执行流程图
awk生命周期
awk内置(预定义)变量
行与列描述
取行
取列
awk中的函数
条件的分类
awk正则详细:
普通正则和awk正则区别
范围表达式
逻辑表达式
算术表达式
特殊模式BEGIN{}和END{}
awk数组
awk 的 判断、循环
if循环
循环
总体练习
易错点:
awk主要是用来格式化文本,也有人称awk是一种语言,类似 C,awk 是三剑客的老大,利剑出鞘,必会不同凡响。
过滤,统计,计算,统计日志
awk读取文件之前执行BEGIN,注意BEGIN读取文件之前就可以执行,后面不跟文件,也可以执行
awk读取文件时,执行BODY块
awk读取文件后,执行END块
格式:<code>awk [参数] 'BEGIN{读取文件前执行的内容}条件{读取文件执行的动作}END{读取完文件执行的内容}' [文件路径]</code>
完整流程示例(无条件要求演示): 读取文件前可以加条件,条件包括正则判断等,继续往下看,看完就明白了~
grep、sed和awk都是读一行处理一行,直至处理完成
内置变量符号
功能描述
$0
代表当前行
$n
代表第n列
NF
记录当前行的字段数(当前行的列数),$NF表示最后一列
NR
用来记录行号(相当于计数器)
FS
指定文本内容字段分隔符(默认是空格)
RS
文本分割符 默认为换行符
OFS
指定打印字段分隔符(默认空格)
ORS
输出的记录分隔符 默认为换行符
名称
描述
说明
行
记录record
每一行结尾默认通过回车分隔
列
记录字段/域field
列与列默认以空格分隔,可以指定分隔符
awk取行字符
NR==1
取出第1行
NR>=1&&NR<=5
取出1到5行 ---范围取
//,//
正则取,谁开头到谁结尾
符号
> < >= <= == !=
<code>-F</code>:指定分隔符,指定每一列结束标记(默认是空格,连续的空格Tab键),-F后也支持正则(案例4)
<code>-v</code>:修改变量
$数字:表示取出某一列
<code>$0</code>:表示整行的内容
补充知识:<code>column -t</code>格式化输出,美化操作
<code>awk '{print $0}' a.sh</code> 输出的内容和<code>cat</code>的效果一样
案例1:取出/etc/passwd文件中的第一列和最后一列
案例2:美化操作
案例3:将/etc/passwd文件的最后一列和第一列互换位置
案例4:取行和取列实现了文本内容“指哪打哪”,取行又取列
取行和取列主要用到的是比较,大于小于等于···
print函数:打印
printf函数:格式化打印
函数搭配字符
搭配字符
功能
%s
代表字符串
%d
代表数字
-
左对齐
+
右对齐
n
占用字符 eg:15代表占用15个字符长度
运算符参考表
awk中的条件有如下的操作👇
<code>//</code>内写正则
awk正则可以精确到某一行,某一列中包含什么内容,或这行不包含什么内容
<code>~</code>:包含
<code>!~</code>:不包含
正则
awk正则
示例
<code>^</code> 代表以什么开头的行
某一列的开头
<code>$3~/^hammer/</code>:第三列以hammer开头的行
<code>$</code> 代表以什么结尾的行
某一列的结尾
<code>$3~/hammer$/</code>:第三列以hammer结尾的行
^$ 代表空行
某一列是空的
<code>/哪里开始/哪里结束/</code> -- 字符取范围,也是正则,经常用
<code>NR==1,NR==5</code>:数字表示范围,第一行开始到第五行结束,类似<code>sed -n '1,5p'</code>
<code>&&</code>:逻辑与
<code>||</code>:逻辑或
<code>|</code>:逻辑非
<code>+</code>:加
<code>-</code>:减
<code>*</code>:乘
<code>/</code>:除
<code>%</code>:取模
模式
含义
BEGIN
awk读文件之前执行
1、进行统计,变量初始化,不涉及读取文件等
2、处理文件之前添加表头
3、用来定义awk变量(不常用)
END
awk读文件之后执行
1、用来接收前面的结果,统计输出结果(常用)
2、awk使用数组,用来接收和输出数组的结果(常用)
END{}用于统计计算
统计方法如下
统计方法
简写
示例描述
i=i+1
i++
计数,统计次数
1-100一共几个数
sum = sum+数值
sum+=数值
求和,累加
前100n项和
注意,i和sum都是变量随便写
可以把END前{}理解为<code>循环</code>
主要应用场景如下👇
统计日志:主要应用为统计日志,类似于统计每个ip出现次数,统计每种状态码出现的次数·····
累加求和,统计
形式
使用
格式:arry[]
arry[0]=hammer arry[1]=ze
print arry[0] arry[1]
批量输出数组内容
for(i in arry)
print i (i是数组下标)
print arry[i] (这样是打印数组内容)
文件用数组统计
arry[$列号]++
for (i in arry)
print i,arry[i]
arry[]++,统计什么就写到[]内,如果统计出现次数,arry[i]代表次数,i代表内容
区别shell数组
shell数组
echo ${arry[0] $arry[1]}
格式:
单分支:if(条件){执行命令}
双分支:if(条件){执行命令}else{}
多分支: if(){}else if(){}else{}
for循环和while循环
for循环格式:<code>for(i="初始值";条件判断;游标){}</code>
while格式:<code>while(条件判断){}</code>
内置变量示例如下:
字段分隔符要指定,单个字符的时候有时候可以不指定,比如冒号;
{}外单引号内要用双引号;
<code>-F</code>如果不指定分隔符建议不要写
<code>FS</code>指定分隔符建议不要写<code>-F</code>,防止冲突
三剑客中是对行操作,不要混淆
数组赋值字母要用引号,不然会被认为是变量,数字没事