Awk命令入门教程详解
时间:2015-05-02 01:27 来源:www.it.net.cn 作者:IT
awk命令的入门教程,awk命令的基本语法,包括了awk外部脚本、awk正则表达式与块、awk条件语句、awk字段分隔符、awk记录号等内容。
第一个awk
代码 1.1: 第一个awk
$ awk '{ print }' /etc/passwd
您将会见到/etc/passwd文件的内容出现在眼前。现在,解释awk做了些什么。调用awk时,我们指定/etc/passwd作为输入文件。执行awk时,它依次对/etc/passwd中的每一行执行print命令。所有输出都发送到stdout,所得到的结果与与执行cat /etc/passwd完全相同。
现在,解释{ print }代码块。在awk中,花括号用于将几块代码组合到一起,这一点类似于C语言。在代码块中只有一条print命令。在awk中,如果只出现print命令,那么将打印当前行的全部内容。
代码 1.2: 屏显当前行
$ awk '{ print $0 }' /etc/passwd
$ awk '{ print "" }' /etc/passwd
在awk中,$0变量表示整个当前行,所以print和print $0的作用完全一样。
代码 1.3: 用一些文字把屏幕填满
$ awk '{ print "hiya" }' /etc/passwd
一、多个字段
代码 1.4: print $1
$ awk -F":" '{ print $1 $3 }' /etc/passwd
halt7
operator11
root0
shutdown6
sync5
bin1
....etc.
代码 1.5: print $1 $3
$ awk -F":" '{ print $1 " " $3 }' /etc/passwd
代码 1.6: $1$3
$ awk -F":" '{ print "username: " $1 "\t\tuid:" $3 }' /etc/passwd
username: halt uid:7
username: operator uid:11
username: root uid:0
username: shutdown uid:6
username: sync uid:5
username: bin uid:1
....etc.
二、外部脚本
代码 1.7: 示例脚本
BEGIN { FS=":" }
{ print $1 }
这两个方法的差别在于如何设置字段分隔符。在这个脚本中,字段分隔符在代码自身中指定(通过设置FS变量),而在前一个示例中,通过在命令行上向awk传递-F":"选项来设置FS。通常,最好在脚本自身中设置字段分隔符,只是因为这表示您可以少输入一个命令行自变量。我们将在本文的后面详细讨论FS变量。
三、BEGIN和END块
通常,对于每个输入行,awk都会执行每个脚本代码块一次。然而,在许多编程情况中,可能需要在awk开始处理输入文件中的文本之前执行初始化代码。对于这种情况,awk允许您定义一个BEGIN块。我们在前一个示例中使用了BEGIN块。因为awk在开始处理输入文件之前会执行BEGIN块,因此它是初始化FS(字段分隔符)变量、打印页眉或初始化其它在程序中以后会引用的全局变量的极佳位置。
awk还提供了另一个特殊块,叫作END块。awk在处理了输入文件中的所有行之后执行这个块。通常,END块用于执行最终计算或打印应该出现在输出流结尾的摘要信息。
四、正则表达式和块
代码 1.8: 正则表达式和块
/foo/ { print }
/[0-9]+\.[0-9]*/ { print }
五、表达式和块
代码 1.9: fredprint
$1 == "fred" { print $3 }
代码 1.10: root
$5 ~ /root/ { print $3 }
六、条件语句
代码 1.11: if
{
if ( $5 ~ /root/ ) {
print $3
}
}
这两个脚本的功能完全一样。第一个示例中,布尔表达式放在代码块外面。而在第二个示例中,将对每一个输入行执行代码块,而且我们使用if语句来选择执行print命令。这两个方法都可以使用,可以选择最适合脚本其它部分的一种方法。
代码 1.12: if if
{
if ( $1 == "foo" ) {
if ( $2 == "foo" ) {
print "uno"
} else {
print "one"
}
} else if ($1 == "bar" ) {
print "two"
} else {
print "three"
}
}
代码 1.13: if
! /matchme/ { print $1 $3 $4 }
代码 1.14: if
{
if ( $0 !~ /matchme/ ) {
print $1 $3 $4
}
}
这两个脚本都只输出不包含matchme字符序列的那些行。此外,还可以选择最适合您的代码的方法。它们的功能完全相同。
代码 1.15: 打印字段等于foo且等于bar的行
( $1 == "foo" ) && ( $2 == "bar" ) { print }
这个示例只打印第一个字段等于foo且第二个字段等于bar的那些行。
七、数值变量!
在BEGIN块中,将整数变量x初始化成零。然后,awk每次遇到空白行时,awk将执行x=x+1语句,递增x。处理完所有行之后,执行END块,awk将打印出最终摘要,指出它找到的空白行数量。
八、字符串化的变量
代码 1.16: 示例字段
2.01
代码 1.17: 1.01x$( )1.01
{ print ($1^2)+1 }
如果做一个小实验,就可以发现如果某个特定变量不包含有效数字,awk在对数学表达式求值时会将该变量当作数字零处理。
九、众多的运算符
awk的另一个优点是它有完整的数学运算符集合。除了标准的加、减、乘、除,awk还允许使用前面演示过的指数运算符“^”、模(余数)运算符“%”和其它许多从C语言中借入的易于使用的赋值操作符。
这些运算符包括前后加减( i++ 、 --foo )、加/减/乘/除赋值运算符( a+=3 、 b*=2 、 c/=2.2 、 d-=6.2 )。不仅如此──我们还有易于使用的模/指数赋值运算符( a^=2 、 b%=4 )。
十、字段分隔符
awk有它自己的特殊变量集合。其中一些允许调整awk的运行方式,而其它变量可以被读取以收集关于输入的有用信息。我们已经接触过这些特殊变量中的一个,FS。前面已经提到过,这个变量让您可以设置awk要查找的字段之间的字符序列。我们使用/etc/passwd作为输入时,将FS设置成":"。当这样做有问题时,我们还可以更灵活地使用FS。
代码 1.18: 另一个字段分隔符
FS="\t+"
以上示例中,我们使用特殊 "+" 规则表达式字符,它表示“一个或多个前一字符”。
代码 1.19: 将FS设置成space
FS="[[:space:]+]"
这个赋值表达式也有问题,它并非必要。为什么?因为缺省情况下,FS设置成单一空格字符,awk将这解释成表示“一个或多个空格或tab”。在这个特殊示例中,缺省FS设置恰恰是您最想要的!
代码 1.20: 字段分隔符示例
FS="foo[0-9][0-9][0-9]"
十一、字段数量
代码 1.21: 字段数量
{
if ( NF > 2 ) {
print $1 " " $2 ":" $3
}
}
十二、记录号
代码 1.22: 记录号
{
#skip header
if ( NR > 10 ) {
print "ok, now for the real information!"
}
}
awk提供了适合各种用途的附加变量,以后探讨。
(责任编辑:IT)
awk命令的入门教程,awk命令的基本语法,包括了awk外部脚本、awk正则表达式与块、awk条件语句、awk字段分隔符、awk记录号等内容。 第一个awk
代码 1.1: 第一个awk
$ awk '{ print }' /etc/passwd
现在,解释{ print }代码块。在awk中,花括号用于将几块代码组合到一起,这一点类似于C语言。在代码块中只有一条print命令。在awk中,如果只出现print命令,那么将打印当前行的全部内容。
代码 1.2: 屏显当前行
$ awk '{ print $0 }' /etc/passwd
$ awk '{ print "" }' /etc/passwd
代码 1.3: 用一些文字把屏幕填满 一、多个字段
代码 1.4: print $1
$ awk -F":" '{ print $1 $3 }' /etc/passwd
halt7 operator11 root0 shutdown6 sync5 bin1 ....etc.
代码 1.5: print $1 $3
$ awk -F":" '{ print $1 " " $3 }' /etc/passwd
代码 1.6: $1$3
$ awk -F":" '{ print "username: " $1 "\t\tuid:" $3 }' /etc/passwd
username: halt uid:7 username: operator uid:11 username: root uid:0 username: shutdown uid:6 username: sync uid:5 username: bin uid:1 ....etc. 二、外部脚本
代码 1.7: 示例脚本
BEGIN { FS=":" }
{ print $1 }
三、BEGIN和END块 通常,对于每个输入行,awk都会执行每个脚本代码块一次。然而,在许多编程情况中,可能需要在awk开始处理输入文件中的文本之前执行初始化代码。对于这种情况,awk允许您定义一个BEGIN块。我们在前一个示例中使用了BEGIN块。因为awk在开始处理输入文件之前会执行BEGIN块,因此它是初始化FS(字段分隔符)变量、打印页眉或初始化其它在程序中以后会引用的全局变量的极佳位置。 awk还提供了另一个特殊块,叫作END块。awk在处理了输入文件中的所有行之后执行这个块。通常,END块用于执行最终计算或打印应该出现在输出流结尾的摘要信息。 四、正则表达式和块
代码 1.8: 正则表达式和块
/foo/ { print }
/[0-9]+\.[0-9]*/ { print } 五、表达式和块
代码 1.9: fredprint 六、条件语句
代码 1.11: if
{
if ( $5 ~ /root/ ) { print $3 } } 这两个脚本的功能完全一样。第一个示例中,布尔表达式放在代码块外面。而在第二个示例中,将对每一个输入行执行代码块,而且我们使用if语句来选择执行print命令。这两个方法都可以使用,可以选择最适合脚本其它部分的一种方法。
代码 1.12: if if
{
if ( $1 == "foo" ) { if ( $2 == "foo" ) { print "uno" } else { print "one" } } else if ($1 == "bar" ) { print "two" } else { print "three" } }
代码 1.13: if
! /matchme/ { print $1 $3 $4 }
代码 1.14: if
{
if ( $0 !~ /matchme/ ) { print $1 $3 $4 } } 这两个脚本都只输出不包含matchme字符序列的那些行。此外,还可以选择最适合您的代码的方法。它们的功能完全相同。
代码 1.15: 打印字段等于foo且等于bar的行
( $1 == "foo" ) && ( $2 == "bar" ) { print }
七、数值变量! 在BEGIN块中,将整数变量x初始化成零。然后,awk每次遇到空白行时,awk将执行x=x+1语句,递增x。处理完所有行之后,执行END块,awk将打印出最终摘要,指出它找到的空白行数量。 八、字符串化的变量
代码 1.16: 示例字段 九、众多的运算符 awk的另一个优点是它有完整的数学运算符集合。除了标准的加、减、乘、除,awk还允许使用前面演示过的指数运算符“^”、模(余数)运算符“%”和其它许多从C语言中借入的易于使用的赋值操作符。 这些运算符包括前后加减( i++ 、 --foo )、加/减/乘/除赋值运算符( a+=3 、 b*=2 、 c/=2.2 、 d-=6.2 )。不仅如此──我们还有易于使用的模/指数赋值运算符( a^=2 、 b%=4 )。 十、字段分隔符 awk有它自己的特殊变量集合。其中一些允许调整awk的运行方式,而其它变量可以被读取以收集关于输入的有用信息。我们已经接触过这些特殊变量中的一个,FS。前面已经提到过,这个变量让您可以设置awk要查找的字段之间的字符序列。我们使用/etc/passwd作为输入时,将FS设置成":"。当这样做有问题时,我们还可以更灵活地使用FS。
代码 1.18: 另一个字段分隔符
FS="\t+"
代码 1.19: 将FS设置成space
FS="[[:space:]+]"
代码 1.20: 字段分隔符示例
FS="foo[0-9][0-9][0-9]"
十一、字段数量
代码 1.21: 字段数量
{
if ( NF > 2 ) { print $1 " " $2 ":" $3 } } 十二、记录号
代码 1.22: 记录号
{
#skip header if ( NR > 10 ) { print "ok, now for the real information!" } } awk提供了适合各种用途的附加变量,以后探讨。 (责任编辑:IT) |