(7)awk命令(每周一个linux命令系列)

    xiaoxiao2025-03-19  28

    简介

    awk是一个强大的文本分析工具,尤其是在应对格式化比较好的日志文件时,简单来说awk就是把文件逐行的读入,以空格为默认分隔符(也可以指定分隔符)将每行切片处理。

    语法

    awk [选项参数] 'script' var=value file(s) 或 awk [选项参数] -f scriptfile var=value file(s)

    awk的工作流程

    awk工作流程是这样的:读入有’\n’换行符分割的一条记录,然后将记录按指定的域分隔符划分域,填充域,$0则表示所有域也就是整条记录(这和正则匹配出来是类似的), 1 表 示 第 一 个 域 , 1表示第一个域, 1,n表示第n个域。默认域分隔符是空格,当然也可以指定分隔符。

    选项参数说明:

    -F fs or --field-separator fs 指定输入文件折分隔符,fs是一个字符串或者是一个正则表达式,如-F:。 -f scripfile or --file scriptfile 从脚本文件中读取awk命令 -v var=value or --asign var=value 赋值一个用户定义变量。

    解析:-F指定了每行的片分隔符是冒号,输出第一个分片和倒数第二个分片中间用逗号分隔

    //假设我们要输出supervisor这个程序的进程号 ,这个命令配合xargs可以方便于结束某些进程 ps -ef|grep 'supervisor'|awk '{print $2}' //输出 1630 比如有如下文件ip.txt 1 134.102.173.43 2 134.102.173.43 3 134.102.171.42 4 134.102.170.9 要统计出现次数最多的IP可以利用以下shell脚本: cat ip.txt | awk '{print $2}' | sort | uniq -c | sort -n -r | head -n 1 最后如果不加head这一组可以统计从多到少的列表

    解析:

    awk ‘{ print $5}’:取数据的低5域(第5列)

    sort:对IP部分进行排序。

    uniq -c:打印每一重复行出现的次数。(并去掉重复行)

    sort -n -r:按照重复行出现的次序倒序排列。

    head -n 5:取排在前5位的IP

    内置变量

    ARGC 命令行参数个数 ARGV 命令行参数排列 ENVIRON 支持队列中系统环境变量的使用 FILENAME awk浏览的文件名 FNR 浏览文件的记录数 FS 设置输入域分隔符,等价于命令行 -F选项 NF 浏览的当前行中分片的个数 NR 已读的记录数 OFS 输出域分隔符 ORS 输出记录分隔符 RS 控制记录分隔符

    常用的就是NF,如果是{print $(NF-1)}就是打印倒数第二个分片

    下面,为了便于举例,我们把/etc/passwd文件保存成demo.txt。

    root:x:0:0:root:/root:/usr/bin/zsh daemon:x:1:1:daemon:/usr/sbin:/usr/sbin/nologin bin:x:2:2:bin:/bin:/usr/sbin/nologin sys:x:3:3:sys:/dev:/usr/sbin/nologin sync:x:4:65534:sync:/bin:/bin/sync

    示例:

    $ awk -F ':' '{print $1, $(NF-1)}' demo.txt

    函数

    awk还提供了一些内置函数,方便对原始数据的处理。

    toupper():用于将字符转为大写。 tolower():字符转为小写。 length():返回字符串长度。 substr():返回子字符串。 sin():正弦。 cos():余弦。 sqrt():平方根。 rand():随机数。

    示例:

    $ awk -F ':' '{ print toupper($1) }' demo.txt

    条件表达式

    awk允许指定输出条件,只输出符合条件的行。

    #只输出包含usr的行。 $ awk -F ':' '/usr/ {print $1}' demo.txt # 输出奇数行 $ awk -F ':' 'NR % 2 == 1 {print $1}' demo.txt root bin sync # 输出第三行以后的行 $ awk -F ':' 'NR >3 {print $1}' demo.txt sys sync #下面的例子输出第一个字段等于指定值的行 $ awk -F ':' '$1 == "root" {print $1}' demo.txt root $ awk -F ':' '$1 == "root" || $1 == "bin" {print $1}' demo.txt root bin

    if 语句

    awk提供了if结构,用于编写复杂的条件,if结构还可以指定else部分

    #输出第一个字段的第一个字符大于m的行。 $ awk -F ':' '{if ($1 > "m") print $1}' demo.txt root sys sync #包含else的 $ awk -F ':' '{if ($1 > "m") print $1; else print "---"}' demo.txt root --- --- sys sync

    本文部分例子出自于廖雪峰老师的博客

    最新回复(0)