目录
一、概述
Awk是一个功能强大的编辑工具,用于在linux/UNIX中对文本和数据进行处理。数据可以来自一个或多个文件,也可以为其他命令的输出,常用作脚本来使用。在执行操作时,Awk逐行读取文本,默认是以空格为分隔符进行分隔,将分割所得的各个字段保存到内建变量中,对比该行是否与给定的模式相匹配,并按模式或者条件执行编辑命令,也可以从脚本中调用编辑命令过滤输出相应内容。
二、Awk的使用
1、用法简述
格式:awk [选项] ’模式或条件{编辑命令}‘ 文件1 文件2
awk -f 脚本文件 文件1 文件2
(1)内置变量
awk提供了许多内置变量:
变量 | 描述 |
FS | 指定每行文本的字段分隔符,缺省为空格或制表位,也即-F "#" |
NF | 当前处理的行的字段个数 |
NR | 当前处理的行的行号(序数) |
$0 | 当前处理的行的整行内容 |
$n | 当前处理的行的第n个字段(第n列) |
在awk中,借用了shell的方法,用位参的概念来顺序的表示行(记录)的不同字段,$1,$2,$3,$4...例如,/etc/passwd中的字段一共7个,即$1..$7。
(2)使用示例
截取硬盘的挂载信息的文件系统列和挂载点列:1,7
[root@ljp test]# df -Th | awk '{print $1,$7}'
文件系统 挂载点
devtmpfs /dev
tmpfs /dev/shm
tmpfs /run
tmpfs /sys/fs/cgroup
/dev/mapper/centos-root /
/dev/sdb1 /data/B
/dev/sda1 /boot
tmpfs /run/user/42
tmpfs /run/user/0
和shell的方法相同的,$0代表所有内容
[root@ljp test]# df -Th | awk '{print $0}'
文件系统 类型 容量 已用 可用 已用% 挂载点
devtmpfs devtmpfs 470M 0 470M 0% /dev
tmpfs tmpfs 487M 0 487M 0% /dev/shm
tmpfs tmpfs 487M 8.5M 478M 2% /run
tmpfs tmpfs 487M 0 487M 0% /sys/fs/cgroup
/dev/mapper/centos-root xfs 19G 19G 89M 100% /
/dev/sdb1 xfs 20G 33M 20G 1% /data/B
/dev/sda1 xfs 497M 165M 333M 34% /boot
tmpfs tmpfs 98M 12K 98M 1% /run/user/42
tmpfs tmpfs 98M 0 98M 0% /run/user/0
2、Awk更多用法示例
(1)输出指定的文本字段
开头,结尾,统计
awk '/^root/{print}' /etc/passwd //输出/etc/passwd中所有以root开头的行
awk '/nologin$/{print}' /etc/passwd //输出/etc/passwd中所有以nologin结尾的行
awk -F : '/bash$/{print|“wc -l”}'/etc/passwd //统计可登录的用户数
除$n外的方式输出指定行
awk 'NR==1,NR==3{print}' /etc/passwd //输出第一至第三行内容
awk 'NR==1 | NR==3{print}' /etc/passwd //输出1,3行的内容
awk '(NR>=1)&&(NR<=3){pint}' /etc/passwd //输出第一到第三行的内容
awk '(NR%2)==1{print}' /etc/passwd //输出所有的奇数行
awk '(NR%2)==0{print}' /etc/passwd //输出所有的偶数行
awk -F : '!($3<900)' /etc/passwd //输出第三个字段不少于900行的内容
(2)使用条件表达进行输出
使用Awk过程中还可以使用条件表达式,也就是if...else语句的捷径,有着和其相同的结果。
awk -F : '{if($3>200){print $0}}' /etc/passwd //输出第三个字段大于200的行
awk -F : '{max=($3>$4)?$3:$4;print max}' /etc/passwd //如果$3>$4,就把其赋值给max并输出
否则将$4赋值给max
输出/etc/passwd中第一字段包含"paul",含七个字段,输出"username:"$1,"shell:"$7
[root@ljp test]# awk -F : '($1~"paul")&&(NF==7){print"username:"$1,"shell:"$7}' /etc/passwd
username:paul shell:/bin/bash
输出指定行的的指定位置字段(记录)
awk -F : 'NR==1,NR==7{print$1,$3}' /etc/passwd //输出1到7行以:分割的1,3字段
[root@ljp test]# awk -F : 'NR==1,NR==7{print$1,$3}' /etc/passwd
root 0
bin 1
daemon 2
adm 3
lp 4
sync 5
shutdown 6
(3)通过管道、双引号调用shell命令
awk -F : '/bash$/{print | "wc -l"}' /etc/passwd
调用wc -l,统计bash结尾的/etc/passwd字段
awk 'BEGIN{while ("w"|getline)n++;{print n-2}}' /etc/passwd
调用w统计在线用户数
awk 'BEGIN{"hostname" | getline;print $0}'
调用hostname查看主机名
BEGIN,读取第一条数据之前,先把分隔符加上后再进去操作;END,在所有数据处理完毕后执行。首先执行BEGIN{}中的操作,然后从指定的文件中逐行读取数据,自动更新NF、NR、$0、$1等内建变量的值,去s执行’模式或条件{编辑指令}‘;最后执行END{}中的后续操作。
(4)计算某一文件内指定列数字内容的总和
比如我们创建一个文件test.txt3:
1
2
3
4
5
6
要求是,将文件内内容进行倒序排序并计算出总和
cat test.txt3 | sort -nr | awk '{sum+=$0;print $0}END {print sum}'
结果如下