Chinaunix首页 | 论坛 | 博客
  • 博客访问: 927814
  • 博文数量: 146
  • 博客积分: 3321
  • 博客等级: 中校
  • 技术积分: 1523
  • 用 户 组: 普通用户
  • 注册时间: 2008-08-29 10:32
文章分类

全部博文(146)

文章存档

2014年(2)

2013年(5)

2012年(4)

2011年(6)

2010年(30)

2009年(75)

2008年(24)

分类:

2009-07-14 19:56:23

    在学习awk时我们常会碰到awk,nawk,oawk,gawk,mawk。这可真是让人有点糊涂了。在网上找到一些关于这几个的资料。
    awk:a w k是一种程序语言,对文档资料的处理具有很强的功能。awk 名称是由它三个最初设计者的姓氏的第一个字母而命名的: Alfred V. Aho、Peter J. We i n b e rg e r、Brian W. Kernighan。
a w k最初在1 9 7 7年完成。1 9 8 5年发表了一个新版本的a w k,它的功能比旧版本增强了不少。a w k 能够用很短的程序对文档里的资料做修改、比较、提取、打印等处理。如果使用C 或P a s c a l 等语言编写程序完成上述的任务会十分不方便而且很花费时间,所写的程序也会很大。

    nawk:
在 20 世纪 80 年代中期,对 AWK 语言进行了更新,并不同程度地使用一种称为 NAWK (New AWK) 的增强版本对其进行了替换。许多系统中仍然存在着旧的 AWK 解释器,但通常将其安装为 oawk (Old AWK) 命令,而 NAWK 解释器则安装为主要的 awk 命令,也可以使用 nawk 命令。Dr. Kernighan 仍然在对 NAWK 进行维护,与 GAWK 一样,它也是开放源代码的,并且可以免费获得。
    gawk: 是 GNU Project 的 AWK 解释器的开放源代码实现。尽管早期的 GAWK 发行版是旧的 AWK 的替代程序,但不断地对其进行了更新,以包含 NAWK 的特性。
    mawk:Mawk 是 AWK 编程语言的解释器。AWK 语言在多媒体数据文件以及文本的检索和处理,算法的原型设计和试验都有广泛的使用。Mawk带给awk新的概念,它实现了在《The AWK Programming Language》(Aho, Kernighan and Weinberger, The AWK Programming Language, Addison-Wesley Publishing, 1988.被认为是 AWK 手册。)中定义的 AWK 语言。Mawk 遵循 POSIX 1003.2 (草案 11.3)定义的 AWK 语言,包含了一些没有在AWK 手册中提到的特色,同时 mawk 提供一小部分扩展。

    目前我们比较倾向于使用gawk和awk。
下面就根据我的理解对awk作一些简单的介绍。

  一.awk三种调用方法,这是程式化的东西,没什么好说的。
   1)命令行方式awk [-F field-separator]'commands' input-file(s)
           这里的commands是真正的awk命令。-F是域分隔符,可选。
   2)第二种方法是将所有的awk命令插入一个文件,并使awk程序可执行,然后用awk命令解释器作为脚本的首行以便通过键入脚本名称来调用它。
   3)将所有的awk命令插入一个单独的文件,然后调用
      awk -f awk-script-file input-file(s)
  二: 以前学过java下的正则表达式,就感觉正则表达式在文本处理方面已是非常强大的,但是学了awk之后发现awk和正则表达式结合起来,功能更加强大。下面是一个例子,虽然完成的功能很一般,但是可以看到awk和正则表达式的强大了。
  1. 首先,我有一个文件test.c如下:
# #include
# #define M 5
# #define N 3

# int k = 0;
# int check_over(int a[]){
#         int i;
#         for(i=0; i#                 if(a[i] == 1)
                         break;
         }
         return M-N-i;
 }
   现在我要将没一行前边多余的那个#去掉,并将新文件存方在test2.c中。那么我就可以用这样一条语句:
awk '{if($1 == "#") print substr($0,2);else print $0}' test.c | cat > test2.c
或者这样的语句:
awk '{if($0 ~/#.*/) print substr($0, 2); else print $0}' test.c | cat > test2.c

   三: 再比如我想要从/etc/passwd文件中读出用户的注册名和用户名,首先我们知道passwd文件中存放了用户的关键信息。系统中每一个合法用户的帐号对应了该文件的一行。每一行的用户记录的各个数据段用:隔开。分别包括注册名,口令,用户标识号,组标识号,用户名,用户主目录,命令解释器shell。那么我们对应的awk脚本文件就可以这样写:文件名是passwd.awk
#!/usr/bin/awk -f
BEGIN{
FS=":";   #定义了分隔符
}
{print $1,"\t",$5}  #打印每一行的第一和第五字段的内容
    执行时直接输入./passwd.awk /etc/passwd就ok了。


   四: 正则表达式中的‘?’的问题。?表示他前边的字符出现0-1次。比较和‘*’的不同,‘*’表示他前边的字符出现0-n次。比如下边这个例子:
along@along-laptop:~/code/shell$ cat test
xyz
yz
xz
xyyyz
along@along-laptop:~/code/shell$ awk '$0 ~/xy?z/{print $0}' test
xyz
xz

along@along-laptop:~/code/shell$ awk '$0 ~/xy*z/{print $0}' test
xyz
xz
xyyyz

五:将awk的输出重定向到一个文件。
along@along-laptop:~/code/shell$ cat hang
1.adf
2.skdf
3.adslfk
4adsf
adflj
sdj

我现在想到的方法有:
awk '$0~/^[0-9]/{print $1}' hang | tee test_out
awk '$0~/^[0-9]/{print $1>"test_out"}' hang
awk '$0~/^[0-9]/{print $1}' hang > test_out


六:实现简单的交互式shell
   现在我想要用awk实现交互式shell,我们举个简单的例子来看:
   从键盘接收一个数字,然后分别打印出这个数字,和这个数字的阶乘。
我的awk脚本文件是这样写的(文件名为jc.awk):
#!/usr/bin/awk -f
BEGIN {
    print "input a number:";
    getline number;   #从键盘接收数据到number
    print "your inout is:" number;    #打印出接收到的内容

    if(number == 0)
        fact=1;
    else
        fact=number;
    for(i=number-1; i>=1; i--)     #计算number的阶乘
        fact*=i;
    print number"!="fact;
}
    赋予jc.awk以执行权限,在终端下直接输入./jc.awk即可。执行结果:
along@along-laptop:~/code/shell$ ./jc.awk
input a number:
4
your inout is:4
4!=24
  
    在命令行下实现简单的交互式shell:
awk 'BEGIN{print "input a number:";getline d;print "your input is:"d}'







阅读(716) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~