linux 命令之awk

awk 是一个强大的文本分析工具,把文件逐行的读入,以空格为默认分割符将每行切片,切开的部分再进行各种分析处理。

awk命令形式:

awk [-F | -f | -v] `BEGIN{} // {command1;command2;....;commandN} END{}` file

[-F | -f | -v]   : 大参数,-F指定分隔符,-f调用脚本,-v定义变量

` `  :  引用代码块

BEGIN : 初始化代码块,在对每一行进行处理之前,初始化代码,(在脚本中主要是引用全局变量,设置FS分隔符)

//    :   匹配样式,可以是字符串或者正则表达式

{}    :  命令代码块,包含一条或者多条命令

;  : 多条命令使用分号分隔

 END : 结尾代码块,在对每一行进行处理之后在执行的代码块,主要是进行最终计算或输出结尾摘要信息。

awk 支持的算术运算:

+  -   *  /  ^  %  ++ -- += -= *=  /= %= 

awk 内置变量:

$0                  表示整个当前行

$n                  每行第n个字段,n不能为0

NF                 字段数量变量

NR                 每行的记录号,多文件处理是记录递增

FNR               每行的记录号,多文件处理时不递增,每个文件都从1开始

FS                  BEGIN时定义分隔符

RS                 输入的记录分隔符,默认为换行符

OFS               输出字段分隔符,默认是空格

ORS              输出记录的分隔符,默认是换行符

示例文件emp_names
$ cat emp_names 
46013     DURHAM JEFF      MOBILE     AL
46015     STEEN BILL       MOBILE     AL
46017     FELDMAN EVAN     MOBILE     AL
46018     SWIM STEVE       UNKNOWN    AL
46019     BOGUE ROBERT     PHOENIX    AZ
46021     JUNE MICAH       PHOENIX    AZ
46022     KANE SHERYL      UNKNOWN    AR
46024     WOOD WILLIAM     MUNCIE     IN
46026     FERGUS SARAH     MUNCIE     IN
46027     BUCK SARAH       MUNCIE     IN
46029     TUTTLE BOB       MUNCIE     IN


$ awk '{print $0}' emp_names    #打印文件emp_names中的所有字段
46013     DURHAM JEFF      MOBILE     AL
46015     STEEN BILL       MOBILE     AL
46017     FELDMAN EVAN     MOBILE     AL
46018     SWIM STEVE       UNKNOWN    AL
46019     BOGUE ROBERT     PHOENIX    AZ
46021     JUNE MICAH       PHOENIX    AZ
46022     KANE SHERYL      UNKNOWN    AR
46024     WOOD WILLIAM     MUNCIE     IN
46026     FERGUS SARAH     MUNCIE     IN
46027     BUCK SARAH       MUNCIE     IN
46029     TUTTLE BOB       MUNCIE     IN
$ awk '{print $1,$2,$3,$4,$5}' emp_names   #打印文件emp_names中多个字段
46013 DURHAM JEFF MOBILE AL
46015 STEEN BILL MOBILE AL
46017 FELDMAN EVAN MOBILE AL
46018 SWIM STEVE UNKNOWN AL
46019 BOGUE ROBERT PHOENIX AZ
46021 JUNE MICAH PHOENIX AZ
46022 KANE SHERYL UNKNOWN AR
46024 WOOD WILLIAM MUNCIE IN
46026 FERGUS SARAH MUNCIE IN
46027 BUCK SARAH MUNCIE IN
46029 TUTTLE BOB MUNCIE IN
$ awk '/AL|AZ/ {print $3,$2,$5}' emp_names #打印文件emp_names中匹配AL 、 AZ样式的多个字段
JEFF DURHAM AL
BILL STEEN AL
EVAN FELDMAN AL
STEVE SWIM AL
ROBERT BOGUE AZ
MICAH JUNE AZ
$ awk '$5~/AR/' emp_names  #在第5个字段中匹配样式,没有指定打印字段,则打印所有字段
46022     KANE SHERYL      UNKNOWN    AR
$ awk '$5!~/AR/' emp_names #在第5个字段中匹配样式,打印出不匹配的所有行(没有指定打印字段,打印所有字段)
46013     DURHAM JEFF      MOBILE     AL
46015     STEEN BILL       MOBILE     AL
46017     FELDMAN EVAN     MOBILE     AL
46018     SWIM STEVE       UNKNOWN    AL
46019     BOGUE ROBERT     PHOENIX    AZ
46021     JUNE MICAH       PHOENIX    AZ
46024     WOOD WILLIAM     MUNCIE     IN
46026     FERGUS SARAH     MUNCIE     IN
46027     BUCK SARAH       MUNCIE     IN
46029     TUTTLE BOB       MUNCIE     IN
$ awk '$5~/AR/ {print $1 ; print $2 ; print $3}' emp_names #将一行中多个字段分行打印
46022
KANE
SHERYL
$ awk '{print $0 | "sort > /tmp/filez"} ' emp_names  #将文件emp_names中字段排序,重定向到/tmp/filez文件中
$ cat /tmp/filez 
46011     TUTTLE BOB       MUNCIE     IN
46012     STEEN BILL       MOBILE     AL
46013     DURHAM JEFF      MOBILE     AL
46017     FELDMAN EVAN     MOBILE     AL
46018     BOGUE ROBERT     PHOENIX    AZ
46019     SWIM STEVE       UNKNOWN    AL
46021     JUNE MICAH       PHOENIX    AZ
46022     KANE SHERYL      UNKNOWN    AR
46027     BUCK SARAH       MUNCIE     IN
46030     FERGUS SARAH     MUNCIE     IN
46045     WOOD WILLIAM     MUNCIE     IN
$ awk -F":" '{print $1}' /etc/passwd   #/etc/passwd是系统自带文件  每行是用:分隔字符,所以需要指定分隔符 也可以使用  awk '{FS=":"} {print $1}' /etc/passwd   这样结果是一样的
root
daemon
bin
sys
sync
games
man
lp
mail
news
...
$ cat awk.list 
BEGIN{FS=":"}
{print $1}
$ awk -f awk.list /etc/passwd  #使用-f调用awk脚本
root
daemon
bin
sys
sync
games
man
lp

$ awk '{FS=":"} {OFS="-"}{print $1,$3}' /etc/passwd #指定输出字段分隔符
root:x:0:0:root:/root:/bin/bash-
daemon-1
bin-2
sys-3
sync-4
games-5
man-6
lp-7
$ awk -F":" '{print "USER_NAME: "$1, "\nNUMBER: "$3}' /etc/passwd  #按照自己想要的格式与内容输出
USER_NAME: root 
NUMBER: 0
USER_NAME: daemon 
NUMBER: 1
USER_NAME: bin 
NUMBER: 2
USER_NAME: sys 
NUMBER: 3
USER_NAME: sync 
NUMBER: 4
USER_NAME: games 
NUMBER: 5


示例文件内容
$ cat inventory 
hammers	5	7.99
drills	2	29.99
punches	7	3.59
drifts	2	4.09
bits	55	1.19
saws	123	14.99
nails	800	.19
screws	80	.29
brads	100	.24

$ awk 'BEGIN {print "ITEM\tQUANTITY\tPRICE\tTOTAL"} {x=x+($2*$3)} {print $1"\t"$2"\t\t"$3"\t"$2*$3} END {print "Total Value of Inventory: " x}' inventory
ITEM	QUANTITY	PRICE	TOTAL  #BEGIN关键字
hammers	5		7.99	39.95
drills	2		29.99	59.98
punches	7		3.59	25.13
drifts	2		4.09	8.18
bits	55		1.19	65.45
saws	123		14.99	1843.77
nails	800		.19	152
screws	80		.29	23.2
brads	100		.24	24
Total Value of Inventory: 2241.66     #END关键字 x最后的值



awk本身是一个编程语言,另外还支持if语句,循环语句;用法类似C语言的编程






郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。