awk历史
AWK 是一种优良的文本处理 工具,Linux 及Unix 环境中现有的功能最强大的数据处理 引擎之一。这种编程及数据操作语言(其名称得自于它的创始人 Alfred Aho 、Peter Weinberger 和 Brian Kernighan 姓氏的首个字母)的最大功能取决于一个人所拥有的知识。 AWK 提供了极其强大的功能:可以进行正则表达式的匹配,样式装入、流控制、数学运算符、进程控制语句甚至于内置的变量和函数。它具备了一个完整的语言所应具有的几乎所有精美特性。实际上 AWK 的确拥有自己的语言: AWK 程序设计语言 , 三位创建者已将它正式定义为“样式扫描和处理语言”。它允许您创建简短的程序,这些程序读取输入文件、为数据排序、处理数据、对输入执行计算以及生成报表,还有无数其他的功能。
最简单地说,AWK 是一种用于处理文本的编程语言工具。AWK 在很多方面类似于 Unix shell 编程语言,尽管 AWK 具有完全属于其本身的语法。它的设计思想来源于 SNOBOL4 、sed 、Marc Rochkind设计的有效性语言、语言工具 yacc 和 lex ,当然还从 C 语言中获取了一些优秀的思想。在最初创造 AWK 时,其目的是用于文本处理,并且这种语言的基础是,只要在输入数据中有模式匹配,就执行一系列指令。该实用工具扫描文件中的每一行,查找与命令行中所给定内容相匹配的模式。如果发现匹配内容,则进行下一个编程步骤。如果找不到匹配内容,则继续处理下一行。
尽管操作可能会很复杂,但命令的语法始终是:
awk '{pattern + action}' {filenames}
其中 pattern 表示 AWK 在数据中查找的内容,而 action 是在找到匹配内容时所执行的一系列命令。花括号({})不需要在程序中始终出现,但它们用于根据特定的模式对一系列指令进行分组。 pattern就是要表示的正则表达式,用斜杠括起来。
gawk 是 AWK 的 GNU 版本
如果说,通常意义上的文本工具或者是编程语言,都是以处理单个文件为单位的话,那么,awk则是好比是一个文本处理机,awk可以接收输入的文件,然后对文本中的文字进入处理然后输出。
awk 使用详解
awk语言的最基本功能是在文件或者字符串中基于指定规则浏览和抽取信息,awk抽取信息后,才能进行其他文本操作。完整的awk脚本通常用来格式化文本文件中的信息。
通常,awk是以文件的一行为处理单位的。awk没接收文件的一行,然后执行相应的命令,来处理文本。
调用awk
有三种方式调用awk:
第一:命令行方式
awk [-F field-separator] 'commands' input-file(s)
其中,commands 是真正awk命令,[-F域分隔符]是可选的。 input-file(s) 是待处理的文件。
在awk中,文件的每一行中,由域分隔符分开的每一项称为一个域。通常,在不指名-F域分隔符的情况下,默认的域分隔符是空格。
例:
如果你的文件中,一行中,是用#号来作为每一项的分割符的时候,那么可以直接使用-F #来指定域分隔符为#
awk -F # 'commands' input-file(s)
从而使文本处理很方便了。
第二种:将所有的awk命令插入一个文件,并使awk程序可执行,然后awk命令解释器作为脚本的首行,一遍通过键入脚本名称来调用。
相当于shell脚本首行的:#!/bin/sh
可以换成:#!/bin/awk
第三种方式是将所有的awk命令插入一个单独文件,然后调用:
awk -f awk-script-file input-file(s)
其中,-f选项加载awk-script-file中的awk脚本,input-file(s)跟上面的是一样的。
awk基本语法特点
传统awk程序的配置如下:
pattern {action} 如果模式匹配,则执行操作
pattern 如果模式匹配,则打印记录(在不指定动作的情况下,默认会打印一条记录)
{action} 没有模式,则针对每条记录,执行操作
任何awk语句都是由模式和动作组成。在一个awk脚本中可能有许多语句,模式部分决定动作合适触发及触发事件。处理即是对数据进行操作。如果省略模式部分,动作将时刻保持执行状态,也就是说,如果模式部分省略了,则操作会针对每条记录无条件的执行。
awk语句中,用/······/来界定正则表达式,用‘ ’单引号来定界语句,实际动作在大括号{}内指明。通常都是:'{ action1;action2 }',{}中,如果有多条语句,例如print if 以及赋值,等,就必须用分号;来间隔,不能用空格作为语句动作分隔符。
模式可以是任何条件语句或者符合语句或者正则表达式。模式包括两个特殊字段 BEGIN和END。BEGIN语句使用在任何文本浏览动作之前,然后文本浏览动作依据输入文本开始执行。END语句用来在awk完成文本浏览动作之后执行。默认情况下,awk总是匹配或者打印行数。
awk读取文件记录的方式
awk每次在文件中读取一行,找到域分隔符(这里是#),设置其域n,直至一新行(这里是缺省记录分隔符\n 换行符),然后划分这一行作为一条记录,接着awk再次启动下一行读进程
test-file文件
域1 域分隔符 域2 域分隔符 域3 域分隔符 域4及换行
(记录1)feiyinzi # 200705 # 24 # 女 \n
(记录2)feiyinzilgd # 200706 # 27 # 男 \n
那么,awk工作流程是这样的:先执行BEGING,然后考试浏览文件,读入有\n换行符分割的一条记录,然后将记录按指定的#域分隔符划分域,填充域$n,那么这里对应的feiyinzi 为$1,200705即为域$2······一次类推,然后$0则表示所有域。然后开始执行模式所对应的动作action,然后开始读入第二条记录······直到所有的记录都读完,然后最后执行END操作。
例程:
我们想要打印每一条记录的姓名,则可以使用一下命令
- awk-F#'{print$1}'test-file
- 执行结果如下:
- feiyinzi
- feiyinzilgd
一般,可以使用BEGIN来打印报告头,END用来打印报告尾
- awk-F#'BEGIN{print"Name\n----------------\n"}{print$1}END{print"endoffile"}'
- 运行结果如下:
- Name
- --------------------------
- feiyinzi
- feiyinzilgd
awk的模式匹配中,正则表达式基本规则不变。
awk内置变量
awk有许多内置变量用来设置环境信息,这些变量可以被改变,下表中给出了最常用的一些变量。
ARGC 命令行参数个数
ARGV 命令行参数排列
ENVIRON 支持队列中系统环境变量的使用
FILENAME awk浏览的文件名
FNR 浏览文件的记录数
FS 设置输入域分隔符,等价于命令行 -F选项
NF 浏览记录的域的个数
NR 已读的记录数
OFS 输出域分隔符
ORS 输出记录分隔符
RS 控制记录分隔符
在对这些变量 设置中,可以放在{}之内,然后用分号;和其他的操作分开。
在实际运用当中,适当合理的使用这些变量,是非常有用的。