1.  入门实例
1.1 显示最近登录的5个帐号:  

[root@localhost ~]# last -n 5 | awk '{print $1}'
root
root
root
root
reboot

1.2 如果只是显示/etc/passwd的账户:

[root@localhost ~]# cat /etc/passwd |awk -F ':' '{print $1}'
root
bin
daemon
adm
lp
sync

1.3 如果只是显示/etc/passwd的账户和账户对应的shell,而账户与shell之间以tab键分割:

[root@localhost ~]# cat /etc/passwd |awk -F ':' '{print $1"\t"$7}' 
root    /bin/bash
bin    /sbin/nologin
daemon    /sbin/nologin
adm    /sbin/nologin
lp    /sbin/nologin
sync    /bin/sync
shutdown    /sbin/shutdown

1.4 如果只是显示/etc/passwd的账户和账户对应的shell,而账户与shell之间以逗号分割,而且在所有行添加列名name,shell,在最后一行添加"blue,/bin/nosh":

[root@localhost ~]# cat /etc/passwd |awk -F ':' 'BEGIN {print "name,shell"}  {print $1","$7} END {print "blue,/bin/nosh"} name,shell'
name,shell
root,/bin/bash
bin,/sbin/nologin
daemon,/sbin/nologin
adm,/sbin/nologin
lp,/sbin/nologin
sync,/bin/sync
shutdown,/sbin/shutdown
....
blue,/bin/nosh

1.5 搜索/etc/passwd有root关键字的所有行:

#awk -F: '/root/' /etc/passwd 
root:x:0:0:root:/root:/bin/bash

这种是pattern的使用示例,匹配了pattern(这里是root)的行才会执行action(没有指定action,默认输出每行的内容)。

搜索支持正则,例如找root开头的: awk -F: '/^root/' /etc/passwd

1.6 搜索/etc/passwd有root关键字的所有行,并显示对应的shell

[root@localhost ~]# awk -F: '/root/{print $7}' /etc/passwd
/bin/bash
/sbin/nologin

1.7 其他小示例:

$ awk '/^(no|so)/' test-----打印所有以模式no或so开头的行。

$ awk '/^[ns]/{print $1}' test-----如果记录以n或s开头,就打印这个记录。

$ awk '$1 ~/[0-9][0-9]$/(print $1}' test-----如果第一个域以两个数字结束就打印这个记录。

$ awk '$1 == 100 || $2 < 50' test-----如果第一个或等于100或者第二个域小于50,则打印该行。

$ awk '$1 != 10' test-----如果第一个域不等于10就打印该行。

$ awk '/test/{print $1 + 10}' test-----如果记录包含正则表达式test,则第一个域加10并打印出来。

$ awk '{print ($1 > 5 ? "ok "$1: "error"$1)}' test-----如果第一个域大于5则打印问号后面的表达式值,否则打印冒号后面的表达式值。

$ awk '/^root/,/^mysql/' test----打印以正则表达式root开头的记录到以正则表达式mysql开头的记录范围内的所有记录。如果找到一个新的正则表达式root开头的记录,则继续打印直到下一个以正则表达式mysql开头的记录为止,或到文件末尾。

2. awk内置变量示例
统计/etc/passwd:文件名,每行的行号,每行的列数,对应的完整行内容:
[root@localhost ~]# awk -F ':' '{print "filename:" FILENAME ",linenumber:" NR ",columns:" NF ",linecontent:"$0}' /etc/passwd
filename:/etc/passwd,linenumber:1,columns:7,linecontent:root:x:0:0:root:/root:/bin/bash
filename:/etc/passwd,linenumber:2,columns:7,linecontent:bin:x:1:1:bin:/bin:/sbin/nologin
filename:/etc/passwd,linenumber:3,columns:7,linecontent:daemon:x:2:2:daemon:/sbin:/sbin/nologin
filename:/etc/passwd,linenumber:4,columns:7,linecontent:adm:x:3:4:adm:/var/adm:/sbin/nologin
filename:/etc/passwd,linenumber:5,columns:7,linecontent:lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin
filename:/etc/passwd,linenumber:6,columns:7,linecontent:sync:x:5:0:sync:/sbin:/bin/sync
filename:/etc/passwd,linenumber:7,columns:7,linecontent:shutdown:x:6:0:shutdown:/sbin:/sbin/shutdown
filename:/etc/passwd,linenumber:8,columns:7,linecontent:halt:x:7:0:halt:/sbin:/sbin/halt
filename:/etc/passwd,linenumber:9,columns:7,linecontent:mail:x:8:12:mail:/var/spool/mail:/sbin/nologin
filename:/etc/passwd,linenumber:10,columns:7,linecontent:uucp:x:10:14:uucp:/var/spool/uucp:/sbin/nologin
filename:/etc/passwd,linenumber:11,columns:7,linecontent:operator:x:11:0:operator:/root:/sbin/nologin
filename:/etc/passwd,linenumber:12,columns:7,linecontent:games:x:12:100:games:/usr/games:/sbin/nologin
filename:/etc/passwd,linenumber:13,columns:7,linecontent:gopher:x:13:30:gopher:/var/gopher:/sbin/nologin
filename:/etc/passwd,linenumber:14,columns:7,linecontent:ftp:x:14:50:FTP User:/var/ftp:/sbin/nologin
filename:/etc/passwd,linenumber:15,columns:7,linecontent:nobody:x:99:99:Nobody:/:/sbin/nologin
filename:/etc/passwd,linenumber:16,columns:7,linecontent:dbus:x:81:81:System message bus:/:/sbin/nologin
filename:/etc/passwd,linenumber:17,columns:7,linecontent:usbmuxd:x:113:113:usbmuxd user:/:/sbin/nologin
filename:/etc/passwd,linenumber:18,columns:7,linecontent:avahi-autoipd:x:170:170:Avahi IPv4LL Stack:/var/lib/avahi-autoipd:/sbin/nologin
filename:/etc/passwd,linenumber:19,columns:7,linecontent:vcsa:x:69:69:virtual console memory owner:/dev:/sbin/nologin
filename:/etc/passwd,linenumber:20,columns:7,linecontent:rtkit:x:499:497:RealtimeKit:/proc:/sbin/nologin
filename:/etc/passwd,linenumber:21,columns:7,linecontent:abrt:x:173:173::/etc/abrt:/sbin/nologin
filename:/etc/passwd,linenumber:22,columns:7,linecontent:haldaemon:x:68:68:HAL daemon:/:/sbin/nologin
filename:/etc/passwd,linenumber:23,columns:7,linecontent:saslauth:x:498:76:"Saslauthd user":/var/empty/saslauth:/sbin/nologin
filename:/etc/passwd,linenumber:24,columns:7,linecontent:postfix:x:89:89::/var/spool/postfix:/sbin/nologin
filename:/etc/passwd,linenumber:25,columns:7,linecontent:ntp:x:38:38::/etc/ntp:/sbin/nologin
filename:/etc/passwd,linenumber:26,columns:7,linecontent:apache:x:48:48:Apache:/var/www:/sbin/nologin
filename:/etc/passwd,linenumber:27,columns:7,linecontent:avahi:x:70:70:Avahi mDNS/DNS-SD Stack:/var/run/avahi-daemon:/sbin/nologin
filename:/etc/passwd,linenumber:28,columns:7,linecontent:pulse:x:497:496:PulseAudio System Daemon:/var/run/pulse:/sbin/nologin
filename:/etc/passwd,linenumber:29,columns:7,linecontent:gdm:x:42:42::/var/lib/gdm:/sbin/nologin
filename:/etc/passwd,linenumber:30,columns:7,linecontent:sshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologin
filename:/etc/passwd,linenumber:31,columns:7,linecontent:tcpdump:x:72:72::/:/sbin/nologin
filename:/etc/passwd,linenumber:32,columns:7,linecontent:zookeeper:x:500:500:Zookeeper:/home/zookeeper:/bin/bash

使用printf替代print,可以让代码更加简洁,易读

awk -F ':' '{printf("filename:%10s,linenumber:%s,columns:%s,linecontent:%s\n",FILENAME,NR,NF,$0)}' /etc/passwd
awk -F ':' '{print "filename:" FILENAME ",linenumber:" NR ",columns:" NF ",linecontent:"$0}' /etc/passwd

   awk中同时提供了print和printf两种打印输出的函数。

   其中print函数的参数可以是变量、数值或者字符串。字符串必须用双引号引用,参数用逗号分隔。如果没有逗号,参数就串联在一起而无法区分。这里,逗号的作用与输出文件的分隔符的作用是一样的,只是后者是空格而已。

   printf函数,其用法和c语言中printf基本相似,可以格式化字符串,输出复杂时,printf更加好用,代码更易懂。

3. awk自定义变量

3.1. 下面统计/etc/passwd的账户人数:

[root@localhost ~]# awk '{count++;print $0;} END{print "user count is ", count}' /etc/passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin
sync:x:5:0:sync:/sbin:/bin/sync......
zookeeper:x:500:500:Zookeeper:/home/zookeeper:/bin/bash
user count is  32

count是自定义变量。之前的action{}里都是只有一个print,其实print只是一个语句,而action{}可以有多个语句,以;号隔开。

3.2. 这里没有初始化count,虽然默认是0,但是妥当的做法还是初始化为0:
[root@localhost ~]# awk 'BEGIN {count=0;print "[start]user count is ", count} {count=count+1;print $0;} END{print "[end]user count is ", count}' /etc/passwd 
[start]user count is  0
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
......
zookeeper:x:500:500:Zookeeper:/home/zookeeper:/bin/bash
[end]user count is  32
3.3. 统计某个文件夹下的文件占用的字节数:
[root@localhost ~]# ls -l |awk 'BEGIN {size=0;} {size=size+$5;} END{print "[end]size is ", size}'
[end]size is  86059

3.4 如果以M为单位显示:
[root@localhost ~]# ls -l |awk 'BEGIN {size=0;} {size=size+$5;} END{print "[end]size is ", size/1024/1024,"M"}'
[end]size is  0.0820723 M

注意,统计不包括文件夹的子目录。

4. 条件语句

统计某个文件夹下的文件占用的字节数,过滤4096大小的文件(一般都是文件夹):

[root@localhost ~]# ls -l |awk 'BEGIN {size=0;print "[start]size is ", size} {if($5!=4096){size=size+$5;}} END{print "[end]size is ", size/1024/1024,"M"}' 
[start]size is  0
[end]size is  0.0508223 M
5. 循环语句

显示/etc/passwd的账户:

[root@localhost ~]# awk -F ':' 'BEGIN {count=0;} {name[count] = $1;count++;}; END{for (i = 0; i < NR; i++) print i, name[i]}' /etc/passwd 
0 root
1 bin
2 daemon
3 adm
4 lp
5 sync
6 shutdown
7 halt
8 mail
9 uucp
10 operator
11 games
12 gopher
13 ftp
14 nobody
15 dbus
16 usbmuxd
17 avahi-autoipd
18 vcsa
19 rtkit
20 abrt
21 haldaemon
22 saslauth
23 postfix
24 ntp
25 apache
26 avahi
27 pulse
28 gdm
29 sshd
30 tcpdump
31 zookeeper

 

 
posted on 2016-08-30 17:36  回家的流浪者  阅读(472)  评论(0编辑  收藏  举报