文本处理工具三剑客之awk

文本处理工具:grep,sed,awk

awk:报告生成器,格式化文本输出

AWK: Aho ,Weinberger,Kernighan

gawk:GNU awk

gawk – pattren  scanning  and  processing  language

基本语法:gawk  [options ] ‘program’ FILE….

    program:PATTERN{ACTION STATEMENTS}

        语句之间用分号分隔

选项:

    -F:指明输入时用到的字段分隔符

    -v:var=value:自定义变量

        blob.png

  1. print

print item1,item2,…..

要点:

    1.以逗号作为分隔符

    2.输出的各item可以是字符串,也可以是数字。也可以是当前记录的字段,变量或者awk的表达式

    3.如果省略item,相当于print $0

实例:

 注意print里面的字符要用引号 引起来  

        blob.png

如果是变量就不要用引号了

        blob.png

省略item相当于print $0,而print “”相当于空,而print “ ”表现是空格

        blob.png

2.变量

    a,内建变量(分隔符)

        FS:inuput field seperator,默认为空白字符  

          OFS: output field seperator,默认为空白字符

          RS:inuput record seperator,输入的换行符

          ORS:output record seperator,输出的换行符

        blob.png

            blob.png

因为此处只定义了输入时换行符为“”,并没有定义输出换行符,所有默认,在输出的时候空格时要换行

,原默认要换行的时候也会换行

           blob.png

        

        NF:number of field,字段数量

               {print  NF} 显示字段数 {print 1}

               ,{print  $NF}显示最后一个字段,类似于{print $1}

          blob.png

          NR: number of field,行数 (如果两个文件一起显示,会直接连在一起,不会分开计数)

                {print  NR} 显示行数

          blob.png 

          FNR:file number of field, 各文件分开计数行数

           blob.png   

          FILENAME:当前文件名

          blob.png

          ARGC:命令行参数的个数

          ARGV:数组,保存的是命令行所给定的各参数

          blob.png

    b.自定义变量

        1.-v var=value

            变量名区分大小写

        blob.png

        2.在program中直接定义

        blob.png

3.printf命令

    格式化输出:printf FORMAT ,item1,item2,….

        1.FORMAT是必须要给出的

        2.不会自动换行,需要显示给出换行控制符,\n

        3.FORMAT需要分别为后面的每个item指定一个格式化符号

    格式符:

        %c:显示字符的ASCII码

        %d,%i:显示十进制整数

        %e,%E:科学计数法数值显示

        %f:显示为浮点数

        %g,%G:以科学计数法或浮点形式显示数值

        %s:显示字符串

        %u:无符号整数

        %%:显示%自身

  换行符记得加上,不然看起来就很蠢了!!

         blob.png  

每个item都要有一个FORMAT,否则item就不成立了,不显示了

        blob.png    

    

    修饰符:

        #[.#]格式符:

            例如%3.1f==>第一个数字控制显示宽度,第二个数字表示小数点后的精度

        -:表示左对齐,默认为右对齐

        +:表示数值的符号 

        表示左对齐           

        blob.png        

        默认为右对齐

        blob.png

4.操作符

    算术运算操作符

        +,-,*,/,^,% 依次为加减乘除 次方取模

        -x:负值

        +x:转换为数值

    字符串操作符:没有符号的操作符,字符串连接

    赋值操作符

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

    比较操作符:

        >,>=,<,<=,!=,==

 blob.png

模式匹配:

    ~:是否匹配

    !~:是否不匹配

逻辑操作符:

    &&: 与

    ||:或

     !:非

显示/etc/passwd文件中uid=0或者大于1000的行显示第1,3列,分隔符为”:“

blob.png

显示/etc/passwd文件中uid大于等于0小于等于1000的行显示第1,3列,分隔符为”:“

blob.png

显示/etc/passwd文件中uid不等于0的行显示第1,3列,分隔符为”:“

blob.png

函数调用:

     function_name(argu1,argu2,…..)  

条件表达式:

      selector ? if-true-expression:if-false-expression

      如果为真执行true,否则执行false

实例:

如果uid大于1000,则usertype为common,否则为system,,输出每行第一列及变量usertype

awk -F: '{$3>=1000?usertype="common":usertype="system";printf "%15s:%-s\n",$1,usertype}' /etc/passwd

blob.png

5.PATTERN

    1.empty:空模式,匹配每一行;

    2./regular expression/:仅处理被此处的模式匹配的行

     !/regular expression/:仅处理被此模式匹配的行之外的行

    例:显示以UUID开头的行,显示第一列,可个为分隔符

       显示不以UUID开头的行,显示第一列,可个为分隔符

    blob.png

    3.relational expression:关系表达式,结果有”真“有”假“,结果为”真“才会被处理

        真:结果为非0值,非空字符串

        假:结果为空字符串或0值

    示例:

    blob.png

    blob.png

    blob.png

    4.line ranges:行范围

        startline,endline: /pat1/,/pat2/不支持直接给出数字格式

    显示从以root开头的行开始,到以nobody开头的行结束,显示第一列,以”:“为分隔符

    blob.png

    显示行号小于10或者大于40的行,取出第一列,分隔符为”:“

    blob.png

    5.NEGIN/END模式

        BEGIN{}:仅在开始处理文件中的文本之前执行一次

        END{}:仅在文本处理完成之后执行一次 

    示例:

    blob.png

    blob.png     

  blob.png

     结果为真处理,为假不处理

    blob.png

    显示偶数行和奇数行

    blob.png

    此例来解释为何上面是奇数和偶数

    说明:i初始值为0,第一行i=!i,则i=1,结果为真,处理,所以上面第一行显示

    第二行时,i初始值为1,i=!i,则i=0,结果为假,不处理,所有上面第二行没显示,

    下面就是循环赋值了,每到技奇数行i=1,偶数行i=0,所以才有上面的效果

    (注意1为真,0为假,非1的结果就是假了,而非0的结果就是真了)

   blob.png

    如果我们使得i的初始值为真,那么结果就和上面的相反了,显示的是偶数行

   blob.png

    6.常用的action

          1.表达式Expressions

          2.控制语句Control statements  :if  while等

          3.组合语句Compound statements :组合语句

          4.输入语句input  statements

          5.输出语句outut  statements :print等

    7.控制语句

        if (condition) { statements } 

          if (condition) { statements }  else  { statements }

          while (condition) { statements }

          do  { statements } while (condition)

          for (expr1;expr2;expr3) { statements }

          break

          continue

          delete  array[index]

          delete array

          exit

          { statements  }

awk控制语句if-else

    语法:if(condition)  statements   [ else  statements]

        if(condition1) {statement1}else if(condition2) {statement2} esle{statement3}

    使用场景:对awk取得的整行或某个字段做条件判断

    示例:

    如果uid大于1000就显示此行中的第1,3列,分隔符为”:“

    blob.png

    如果uid大于1000则显示为conmmon user,否则显示system user,并显示第1,3列,分隔符为”:“

    blob.png

    说明 90分以下为very good 60-90为good,60分以下为不及格  blob.png

    以/dev开头的行,分隔符为%,取第一列,然后显示的行中默认可个为分隔符,最后一行如果大于20,则显示第1行和最后一行

    blob.png

awk控制语句=====while循环

语法:while(condition){statement}

条件为”真“,进入循环;条件为”假“,退出循环

使用场景:

    对一行内的多个字段注意类似处理时使用

    对数组中那个的各元素逐一处理时使用

示例:

    说明:文件为/etc/grub.cfg,匹配以任意数量的空格开头后面跟Linux16的行,做while循环,初始值i=1,判断题条件为i<NF(每行字段数),

      i++自增,打印内容为每行的每个字段,以及此字符个数。默认分隔符为" "

blob.png

    说明:在上面的基础上加了一个判断条件,字段中字符分个数大于等于10,打印内容为每行的每个字段,以及此字符个数。默认分隔符为" "

blob.png

awk控制语句=====do-while循环

语法:do {statement;…}while(condition)

意义:无论真假,至少执行一次循环

示例:

    blob.png

    说明不同:

    后面的i没有争议,那么i++和++i的却别就在于,先后顺序,

    第一个是先显示i,然后才自增赋值的,所以值为

    第二个是先自增赋值,然后才显示i的,所以值为1

    blob.png

awk控制语句===for循环

语法:for(expr1;expr2;expr3){statement;…}

常见用法:

    for(variable assignment;condition;iteration process){for-body}

特殊用法:能够遍历数组中的元素;

    语法: :for(var in array) {for-body}

示例:

awk '/^[[:space:]]*linux16/{for(i=1;i<=NF;i++) {print $i,length($i)}}' /etc/grub2.cfg

blob.png

性能比较:

time (awk 'BEGIN{total=0;for(i=0;i<=10000;i++){total+=i;};print total;}')
time(total=0;for i in {1..1000000};do total=$(($total+i));done;echo $total)
time(for ((i=0;i<=1000000;i++));do let total+=i;done;echo $total)

结果很显然是awk运算最快,想想也知道了,这章博客主要内容就是awk,做这个比较肯定想体现akw是有多牛逼咯

blob.png

awk控制语句====>switch语句

语法:swicth(expression){case VALUE1 or /REGEXP/:statement;case VALUE2 or /REGEXP2/:statement;…;default:statement}

break和continue

示例:

break表示当i=66的时候中断此循环,所以结果是1加到65

continue表示当i为偶数的时候终止了本轮循环,所以结果为奇数相加

blob.png

break[n]

continue[n]

next:

提前结束对本行处理而直接进入下一轮处理(awk自身循环)

说明:当uid为奇数时,提前结束本行,跳过本行要处理的,

blob.png

awk数值:array[index-expression]

index-expression:

    1.可使用任意字符串;字符串要使用双引号括起来

    2.如果某数组元素事先不存在,在引用时,awk会自动创建此元素,并将其值初始化为“空串”

若要判断数组中是否存在某元素,要使用“index in array”格式进行遍历

示例:

blob.png

 awk ‘!a[$0]++’ dupfile

若要遍历数组中的每个元素,要使用for循环

for(var in array) {for-body}

注意:var会遍历array的每个索引

示例:

blob.png

说明:统计tcp开头的单词中最后一字段出现次数

blob.png

说明:统计第一段ip出现的次数

blob.png

awk函数:

    rand():返回0和1之一个随机数

[root@localhost ~]# awk 'BEGIN{srand(); for (i=1;i<=10;i++)print int(rand()*100) }'

blob.png

字符串处理:

length([s]):返回指定字符串的长度

sub(r,s,[t]):对t字符串进行搜索r表示的模式匹配的内容,并将第一个匹配的内容替换成s

    echo "2008:08:08 08:08:08" | awk 'sub(/:/,“-",$1)'

gsub(r,s,[t]):对t字符串进行搜索r表示的模式匹配的内容,并全部替换为s所表示的内容

    echo "2008:08:08 08:08:08" | awk ‘gsub(/:/,"",$1)'

blob.png

split(s,array ,[r]):以r为分隔符,切割字符s,并将切割后的结果保存至array所表示的数组中,第一个索引值为1

第二个索引值为2…

blob.png

自定义函数

格式

    function name (parameter,parameter,….){

            statements

            return exprossion

    }

示例:

#!/bin/bash
function max(v1,v2) {
v1>v2?var=v1:var=v2
return var
}
BEGIN{a=3;b=2;print max(a,b)}

blob.png

  1 #!/bin/bash
  2 function max(v1,v2) {
  3 v1>v2?var=v1:var=v2
  4 return var
  5 }
  6 BEGIN{print max(a,b)}

blob.png

awk中调用shell命令

system命令

空格是awk中的字符串连接符,如果system中需要使用awk中的变量可以使用空格分隔,或者说除了awk

的变量外其他的一律用“”引用起来

blob.png

awk脚本

将awk程序写成脚本,直接调用或执行

示例:

blob.png

blob.png

向awk脚本传递参数

格式:

    awkfile var=value var2=value2… Inputfile

[root@localhost bin]# cat test.awk 
#!/bin/awk -f
{if($3<=min||$3>=max)print $1,$3}
[root@localhost bin]# test.awk -F: min=10 max=1000 /etc/passwd

blob.png

练习

1 、 统计/etc/fstab文件中每个文件系统类型出现 的次数

awk '/^UUID/{fs[$3]++}END{for(i in fs) {print i,fs[i]}}' /etc/fstab

blob.png

2、 、 统计/etc/fstab 文件中每个单词出现的次数

[root@localhost bin]# awk '{for(i=1;i<=NF;i++){count[$i]++}}END{for(i in count) {print i,count[i]}}' /etc/fstab
man 1
and/or 1
/mnt 1
maintained 1
xfs 4
14:09:19 1
UUID=b39702a5-31f8-4fca-96cc-3389a0a58059 1
Accessible 1
# 7
are 1
defaults 5
blkid(8) 1
/ 1
0 13
See 1
3 1
Mon 1
Created 1
on 1
usrquota,grpquota 1
mount(8) 1
ext4 2
acl 1
anaconda 1
fstab(5), 1
/boot 1
/testdir 1
/usr 1
UUID=bd915a87-493a-415b-8d2f-8cedaab84792 1
findfs(8), 1
2016 1
/home 1
'/dev/disk' 1
UUID=5bc0405e-cf7a-4d60-8c0c-a6daa1dd71d2 1
by 2
/etc/fstab 1
UUID=12294f2d-4b7d-4f64-a8b7-1522fe51d0b2 1
pages 1
UUID=d8150c22-3804-4d3e-bd18-8f44e93bb978 1
more 1
25 1
info 1
UUID=8d687919-88d4-4c2a-9e0b-473cd13bb785 1
swap 2
Jul 1
UUID=14efdeb1-9880-49dc-aaa0-321c4eb4816a 1
filesystems, 1
reference, 1
for 1
under 1

原创文章,作者:qiuwei,如若转载,请注明出处:http://www.178linux.com/47950

(0)
qiuweiqiuwei
上一篇 2016-09-22
下一篇 2016-09-22

相关推荐

  • Linux 的发展史

    前言 l  免费源码开放 l  安全性高,漏洞修补快 l  多任务、多使用者 l  多平台支持 l  设备要求低,不耗资源 ……      看到这一系列的优点,在IT人的脑海里只会浮出一个名字Linux. 如果还不够直观的话,有这么一个数据, 显示前500系统中的485…

    Linux干货 2016-10-14
  • 一起学DNS系列(十五)DNS查询工具之NSLOOKUP的使用

    原创作品,允许转载,转载时请务必以超链接形式标明文章 原始出处 、作者信息和本声明。否则将追究法律责任。http://jeffyyko.blog.51cto.com/28563/259092    上一节里我们讨论了有关DIG工具的用法,本节将对windows下nslookup工具的一些主要命令进行描述。  …

    2015-03-17
  • 推荐-LVS专题: LVS+Keepalived并使用DNS轮询实现Director的高可用和负载均衡

    LVS专题: LVS+Keepalived并使用DNS轮询实现Director的高可用和负载均衡 前言 什么是KeepAlived 实验介绍 实验拓扑 实验环境 实验步骤 配置KeepAlived(1) 实现Director 的VIP互为主从 测试 配置LVS 配置KeepAlived(2) 测试LVS 配置RS的IP和web服务 配置DNS 最终测试 总结…

    Linux干货 2016-04-09
  • 磁盘文件挂载与卸载

    挂载(mount)何为挂载?挂载指将文件系统与根文件系统的某个现存的目录建立起来的关联关系,这样我们就可以将目录作为访问磁盘文件的入口,进行存取交互。挂载点:挂载点指的是被挂载的对象,通常挂载点是一个目录,不过有时候也有文件作为挂载点格式:mount 设备 挂载点 ;此挂载方法味临时挂载,只在当前的shell中有效,退出则清除挂载关联设备文件在/dev/sd…

    Linux干货 2017-04-24
  • ansible进阶(roles应用)

    ansible 进阶 一、roles简介 一个项目从开始到结束,不是简单几十个playbook就可以完事了,当文件数很多,有上百个的话,仅通过简单的includes不停的引用,那最终的结果错综复杂。这个时候ansible roles就可以很好的发挥它的作用了。 roles,字面意思是角色的含义,可以理解为有相互关联功能的集合。我们把安装ntp、mem、ngi…

    2017-01-05
  • 浅谈RPM

    浅谈RPM    [先絮叨下编译啊]   1、 库:其实就是一个程序模块(它没有执行入口,不能独立执行,只能被能独立运行的程序调用时执行)你可以把它想象成工具螺丝刀,可执行的程序是就是你自己;螺丝刀能自己干活吗?没有螺丝刀能拧螺丝吗?或者说你现在制作一个? 螺丝刀可以实现这个功能但需要你来执行这个动作。   2、静态编译:将程序所需要的所有的库都编…

    Linux干货 2015-04-27