awk学习笔记

AWK 是一种用于处理文本的编程语言工具,在很多方面类似于 shell 编程语言。

AWK有两种运行方式

命令行

$ echo "\n\n" | awk '{print("Hello World!");}'

  Hello World!
  Hello World!
  Hello World!

文件执行方式

$ cat hello.txt
  hello
  hello
  hello

$ cat hello.awk 
  {
      print("Hello World!");
  }

$ awk -f hello.awk hello.txt
  Hello World!
  Hello World!
  Hello World!

AWK程序结构

BEGIN{
    print("程序预处理部分,只在开始文件扫描前执行一次");
}
{
    print("程序主体部分,执行次数取决于目标处理文件的行数,每一行被扫描到时都会触发一次执行"); 
}
END{
    print("所有文件扫描完成后的触发执行一次,通常用作收尾的统计处理");
}

#以上3个部分都不是必须的,只要有其中一部分就可以正常直行。

处理单元(记录)、域(字段)

默认awk是用\n来划分处理单元,用空格将处理单元划分为多个域。一个处理单元相当于数据库里的一条记录,一个域相当于一个字段。awk用$0,$1,$2….$n来表示域,其中$0为当前处理单元,$1表示第一个域,以此类推,$n表示第N个域。

$ cat hello.txt
  Hello World!
  Hello World!
  Hello World!

$ cat hello.awk
  {
    print($0, "\t|",$1, "|\t",$2)
  }

$ awk -f hello.awk hello.txt
  Hello World!     | Hello |     World!
  Hello World!     | Hello |     World!
  Hello World!     | Hello |     World!

变量

  • awk不是强类型语言,变量无需声明,且可以随时改变赋值的类型
  • awk里的变量都是全局的,所以使用变量时需要注意
  • 变量可以在程序中赋值,也可以通过命令调用时对变量赋值
$ cat hello.awk
  BEGIN{
  print(say);
  }
  {
  ++i;
  print(i);
  }
  END{
  print("end");
  }

$ cat hello.awk|awk -v i=100 -v say="hello" -f hello.awk
  hello
  101
  102
  103
  104
  105
  106
  107
  108
  109
  110
  end

系统变量

  • NF 当前记录的域数量
  • NR 已处理的记录数量
  • FS 在程序中动态改变域分隔符
  • FNR 当前记录数,与NR不同的是,这个值会是各个文件自己的行号
  • RS 输入的记录分隔符,默认是换行符
  • OFS 输出字段分隔符,默认是空格
  • ORS 输出的记录分隔符,默认是换行符
  • FILENAME 当前输入文件名
  • $0 当前处理单元
  • $1~$n 当前处理单元的第n个字段,字段间由FS分隔

数组

#定义数组
array[1]=1;
array['a']="a";

#通过split创建数组

# split(content, array, separator)

$ echo ""|awk 'BEGIN{s="1,2,3"}{split(s, array, ",");print(array[2])}'
  2

#遍历数组
for(key in array) {
...
}

for(i=1;i<length(array);i++) {
...
}

#删除数组
delete array[1]

运算符

类型 操作符
赋值语句 =
+=
-=
*=
/=
%=
^=
**=
逻辑或 \ \
逻辑与 &&
匹配 ~
~!

流程控制

#判断
if (condation) {
...
} else if (condation) {
...
} else {
...
}

#循环
for (i=0;i<100;i++) {
...
}

#遍历
for (i in list) {
...
}

#循环
while(condation){
...
}

#分支判断
switch(condation) {
case condation1:
break;
...
case condationn:
break;
default:
...
}

自定义函数

function funName(p1,p2...) {
}

参数为局部变量,函数内的其他变量会自动声明为全局变量

控制语句

continue 进入下一循环
break 跳出循环
next 跳过当前记录的处理,处理下一记录
return 函数返回
exit 退出程序