Linux awk案例
目录
- 1. 查询时间超过2000毫秒的请求
- 2. 查询指定列组合出现的次数
- 3. 统计所有文件的大小
- 4. 获取大于指定大小的文件名,并按照从大到小排序
- 5. grep指定字段后,使用awk列转行
- 6. 查询第四个字段等于指定值的内容
1. 查询时间超过2000毫秒的请求
✅log: 20231119-1.log
2023:11:19 09:07:10 SPLEND=2000 请求开始 110 END
2023:11:19 09:07:11 SPLEND=1000 请求开始 120 END
2023:11:19 09:07:12 SPLEND=3000 请求开始 119 END
2023:11:19 09:07:13 SPLEND=4000 请求开始 156 END
2023:11:19 09:07:14 SPLEND=4000 请求开始 157 END
⏹查询时间超过2000毫秒的请求
grep -a SPLEND ./20231119-1.log | awk 'BEGIN {FS="="} {if($NF>2000) print $0}'
👇结果
2023:11:19 09:07:10 SPLEND=2000 请求开始 110 END
2023:11:19 09:07:12 SPLEND=3000 请求开始 119 END
2023:11:19 09:07:13 SPLEND=4000 请求开始 156 END
2023:11:19 09:07:14 SPLEND=4000 请求开始 157 END
2. 查询指定列组合出现的次数
✅log: 20231119-2.log
你好 世界 110120 AAA
世界 你好 112123 BBB
你好 世界 343434 CCC
世界 你好 343434 DDD
世界 你好 565656 WWW
hello world 23232 EEE
hello world 23423 FFF
world hello 23232 GGG
world hello 34344 HHH
⏹查询第2列和第1列组合之后,出现的次数
cat ./20231119-2.log | awk '{cnt[$2" "$1]+=1;} END {for (i in cnt) print i,cnt[i]"回"}'
👇结果
world hello 2回
hello world 2回
你好 世界 3回
世界 你好 2回
3. 统计所有文件的大小
⏹有如下文件
fengyehong@ubuntu:~/uwsgi-2.0.18/core$ ls -l ./m*.c
-rw-rw-r-- 1 fengyehong fengyehong 32766 Feb 9 2019 ./master.c
-rw-rw-r-- 1 fengyehong fengyehong 11714 Feb 9 2019 ./master_checks.c
-rw-rw-r-- 1 fengyehong fengyehong 7616 Feb 9 2019 ./master_events.c
-rw-rw-r-- 1 fengyehong fengyehong 49900 Feb 9 2019 ./master_utils.c
-rw-rw-r-- 1 fengyehong fengyehong 31952 Feb 9 2019 ./metrics.c
-rw-rw-r-- 1 fengyehong fengyehong 6147 Feb 9 2019 ./mount.c
-rw-rw-r-- 1 fengyehong fengyehong 11774 Feb 9 2019 ./mule.c
- total:定义了一个变量
- $5:第5个字段,即文件大小的字段。
- 通过
{total += $5}
累加完成之后,在END{ }
代码块中将结果打印出来
ls -l ./m*.c | awk '{total += $5} END {print "总大小: ", total/1024, "KB"}'
4. 获取大于指定大小的文件名,并按照从大到小排序
if($5 > 100000)
:指定获取大于100000byte的文件-k5,5
:使用第5列作为排序的关键字段n
:使用数字顺序排序r
:逆向排序,从大到小排序
# 从小到大排序
ls -l ~/uwsgi-2.0.18/core | awk '{if($5 > 100000) print $0}' | sort -k5,5n
# 从大到小排序
ls -l ~/uwsgi-2.0.18/core | awk '{if($5 > 100000) print $0}' | sort -k5,5nr
5. grep指定字段后,使用awk列转行
✅info.txt
110120 SPLREQUEST name=東川雄一 AAA memberID=1 tel=080-1111-1111 SPLEND ExecTime=200 ResultCode=200
123456 SPLREQUEST name=西村祐二 BBB memberID=2 tel=080-2222-2222 SPLEND ExecTime=300 ResultCode=200
123444 SPLREQUEST name=南山裕三 CCC memberID=3 tel=080-3333-3333 SPLEND ExecTime=200 ResultCode=200
123434 SPLREQUEST name=北岡優四 memberID= tel=080-4444-4444 SPLEND ExecTime=400 ResultCode=200
345345 SPLREQUEST name=田中様 EEE memberID=5 tel=080-5555-5555 SPLEND ExecTime=500 ResultCode=200
674545 SPLREQUEST name=竹下様 FFF memberID=6 tel=080-6666-6666 SPLEND ExecTime=400 ResultCode=200
🤪需求:从文件中获取第一个字段,name字段,tel字段,ExecTime字段,并转为一行
- 获取每个字段可以使用
-e
配置项,然后配合正则表达式\S*
获取非空内容 -o
:仅获取匹配到的内容,不获取行的其他内容- 仅使用grep命令得到的结果都不在一行上,而应该是每4行一组
- 使用
awk
命令的ORS
指定文本输出时的换行符 ORS = (NR % 4 == 0) ? "\n" : ","
- 如果当前行号不是4的倍数,还不该换行,将换行符指定为
,
,不会引起换行,从而实现列转行。 - 如果当前行号是4的倍数,说明每4行已经变为一行,此时将换行符置为
\n
,实现没一行有4个字段。
- 如果当前行号不是4的倍数,还不该换行,将换行符指定为
grep -a -o -e "^\S*" -e "name=\S*" -e "tel=\S*" -e "ExecTime=\S*" ./info.txt | awk 'ORS = (NR % 4 == 0) ? "\n" : ","'
6. 查询第四个字段等于指定值的内容
✅info.txt
110120 SPLREQUEST name=東川雄一 994 memberID=1 tel=080-1111-1111 SPLEND ExecTime=200 ResultCode=200
123456 SPLREQUEST name=西村祐二 889 memberID=2 tel=080-2222-2222 SPLEND ExecTime=300 ResultCode=200
123444 SPLREQUEST name=南山裕三 994 memberID=3 tel=080-3333-3333 SPLEND ExecTime=200 ResultCode=200
123434 SPLREQUEST name=北岡優四 110 memberID= tel=080-4444-4444 SPLEND ExecTime=400 ResultCode=200
345345 SPLREQUEST name=田中様 110 EEE memberID=5 tel=080-5555-5555 SPLEND ExecTime=500 ResultCode=200
674545 SPLREQUEST name=竹下様 114 FFF memberID=6 tel=080-6666-6666 SPLEND ExecTime=400 ResultCode=200
- 需求:查询第四个字段的值为994所在行的内容
- 每个字段使用Tab分隔,所以使用
-F'\t'
awk -F'\t' '$4 == "994" {print $0}' ./info.txt | nkf -w8