文本三劍客之AWK

文本三劍客—-awk(3)

awk簡介

awk是一個強大的文本分析工具,與grep(查找)、sed(編輯)一并稱為“文本處理三劍客”。awk最強大的功能是對數據分析并生成報告。

awk有3個不同版本: awk、nawk和gawk,未作特別說明,一般指gawk,gawk是AWK的GNU版本。

awk其名稱得自于它的創始人 Alfred Aho 、Peter Weinberger 和 Brian Kernighan 姓氏的首個字母。awk能讀取輸入文件、為數據排序、處理數據、對輸入執行計算以及生成報表,還有無數其他的功能。

工作原理

一次讀取一行文本,按輸入分隔符進行切片,切成多個組成部分,將每片直接保存在內建的變量中,$1,$2,$3….,引用指定的變量,可以顯示指定斷,或者多個斷。如果需要顯示全部的,需要使用$0來引用。可以對單個片斷進行判斷,也可以對所有斷進行循環判斷。其默認分隔符為空格

  1. 按行讀取文本(文件的每一行稱為記錄)
  2. 按輸入分隔符進行切片
  3. 對切片自動生命變量 $1,$2…(域標識;$0為所有域)
  4. 對指定目標做處理(處理及打印等)

語法格式

awk [options] ‘program’ FILE……

[options]
–F:指明輸入時的分隔符
–v:自定義變量
–f:調用awk腳本
program:pattern{action statements;..}
-pattern:觸發條件
-action statements:對數據處理動作

步驟

  1. 執行BEGIN{action;…}
    BEGIN在輸入之前執行,通常用來打印表頭,變量初始化。
  2. 讀取,執行pattern{action;…}
    默認執行{ print }
  3. 執行END{action;…}
    讀取到打印結束后執行,通常用作分析結果,信息匯總。

變量

內置變量

  • FS:輸入字段分隔符
  • OFS:輸出字段分隔符
  • RS:輸入記錄分隔符
  • ORS:輸出記錄分隔符
  • ARGC:命令行參數的個數
  • ARGV:數組,保存命令行給定的各參數
  • NF:字段數量
  • NR:行號
  • FNR:個文件分別計數,行號
  • FILENAME:當前文件名

自定義變量

  1. 選項位置定義:-v var=hello
  2. 在program中定義:awk ‘BEGIN{test=”hello”;print test}’

字符串處理

  1. length([s]) :返回指定字符串的長度
  2. sub(r,s,[t]) :對t字符串進行搜索r 表示的模式匹配的內容,并將第一個匹配的內容替換為s
    echo “2008:08:08 08:08:08″ | awk ‘sub(/:/,”-“,$0)’
  3. gsub(r,s,[t]) :對t字符串進行搜索r表示的模式匹配的內容,并全部替換為s所表示的內容
    echo “2008:08:08 08:08:08″ | awk ‘gsub(/:/,”-“,$0)’
  4. split(s,array,[r]) :以r為分隔符,切割字符串s,并將切割后的結果保存至array 所表示的數組中,第一個索引值為1, 第二個索引值為2,…
    netstat -tan | awk ‘/^tcp>/{split($5,ip,”:”);count[ip[1]]++} END{for (i in count) {print i,count[i]}}’

Printf命令

  1. print不需要指定,printf需要指定format
  2. printf后面的字串需要使用雙引號
  3. 字串定義后的內容需要使用”,”分隔,后面直接跟Item1,item2….
  4. format用于指定后面的每個item的輸出格式
  5. printf語句不會自動打印換行符\n

格式符

  1. %s: 顯示字符串
  2. %d,%i: 顯示十進制整數
  3. %e,%E: 科學計數法數值顯示
  4. %f: 顯示為浮點數
  5. %g,%G: 以科學數法或浮點形式顯示數值
  6. %c: 顯示字符的ASCII碼
  7. %u: 無符號整數
  8. %%: 顯示%號自身,相當于轉義

修飾符

  1. N: 顯示寬度
  2. -: 左對齊(默認為右對齊)
  3. +: 顯示數值符號

操作符

  • 算數
    x+y, x-y, x*y, x/y, x^y, x%y
  • 賦值
    =, +=, -=, *=, /=, %=, ^=,++, —
  • 比較
    ==, !=, >, >=, <, <=
  • 模式匹配符
    ~:左邊是否和右邊匹配包含!~:是否不匹配
  • 邏輯
    &&,||,!

awk -F: ‘{printf “Username: %-15s,UID:%d\n”,$1,$3}’ /etc/passwd

PROGRAM

pattern

  1. )默認匹配每一行
  2. )/pattern/:僅處理匹配到的行
  3. )/pattern1/,/pattern2/:處理 pattern1 到 pattern2 之間
  4. )關系表達式:真:非0假:空或0

action

  1. )Expressions: 算術,比較表達式等
  2. ) Control statements :if, while等
  3. ) Compound statements :組合語句
  4. ) input statements
  5. ) output statements :print等

控制語句

  1. if-else
    awk ‘BEGIN{ test=100;if(test>90){print “very good”} else if(test>60){ print “good”}else{print “no pass”}}’
    成績為100;大于90打印“very good”;大于60打印“good”;其余打印“no pass”
  2. while 循環
    條件”真”,進入循環;條件”假”,退出循環
    awk ‘/^[[:space:]]*linux16/{i=1;while(i<=NF) {if(length($i)>=10){print $i,length($i)}; i++}}’ /etc/grub2.cfg
    以空白符開頭后跟”linux16″的行中,把字符數大于10的字符串打印出來。
  3. do-while 循環
    無論真假,至少執行一次
    awk ‘BEGIN{ sum=0;i=0;do{sum+=i;i++;}while(i<=100);print sum}’
    累加
  4. for 循環
    遍歷
    awk ‘/^[[:space:]]*linux16/{for(i=1;i<=NF;i++) {print$i,length($i)}}’ /etc/grub2.cfg
  5. switch 語句
  6. break 和 continue
    awk ‘BEGIN{sum=0;for(i=1;i<=100;i++){if(i%2==0)continue;sum+=i}print sum}’
    awk ‘BEGIN{sum=0;for(i=1;i<=100;i++){if(i==66)break;sum+=i}print sum}’
  7. next
    提前 結束對本行處理而直接進入下一行處理
    seq {1,20} | awk -F: ‘{if($1%2==0)next ; print $1}’
    打印奇數行

數組

  1. )可使用任意字符串;字符串要使用雙引號括起來
  2. )如果某數組元素事先不存在,在引用時,awk 會自動創建此元素,并將其值初始化為“空字符串(即為”假”)”
  • 若要判斷數組中是否存在某元素,要使用“index in array”格式進行遍歷

示例練習:

[root@localhost ~]# awk -F: '$NF ~ /bash$/{print $1,$NF}' /etc/passwd
root /bin/bash
wang /bin/bash
lao /bin/bash
cai /bin/bash

 

[root@localhost ~]# awk -F: '$NF=="/bin/bash"{print $1,$NF}' /etc/passwd
root /bin/bash
wang /bin/bash
lao /bin/bash
cai /bin/bash

 

[root@localhost ~]# cat f
aa
bb
cc
dd
aa
bb
cc
dd
[root@localhost ~]# awk '!arr[$0]++' f
aa
bb
cc
dd
[root@localhost ~]# awk '{!arr[$0]++;print $0,arr[$0]}' f
aa 1
bb 1
cc 1
dd 1
aa 2
bb 2
cc 2
dd 2

[root@localhost ~]# awk '/^UUID/||/^\/dev/{fs[$3]++} END{for (i in fs){print i,fs[i]}}' /etc/fstab
swap 1
xfs 4

 

[root@localhost ~]# 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
maintained 1
xfs 4
Accessible 1
Thu 1
UUID=63af8e82-3a2a-40ed-8f76-64f56502ee1c 1are 1
defaults 4
blkid(8) 1
/ 1
/dev/mapper/cl-root 1
0 10

 

[root@localhost ~]# echo "Yd$C@M05MB%9&Bdh7dq+YVixp3vpw" | awk -F "[^[:digit:]]" '{for(k=1;k<=NF;k++){a[$k]}} END{for(i in a) {printf "%s",i}printf "\n"}'
79053

 

原創文章,作者:kstg5663294,如若轉載,請注明出處:http://www.www58058.com/81635

(6)
kstg5663294kstg5663294
上一篇 2017-07-17 17:19
下一篇 2017-07-17 19:34

相關推薦

  • Linux下的SSH端口轉發

    通常情況下兩個不同的網絡之間總會開放某一些特定的端口用于通訊使用,而SSH所使用的22端口通常就在開放之列?;赟SH的端口轉發就是利用SSH作為中間的代理,達到繞過兩個網絡之間的限制,順利的進行任意的端口的訪問。端口轉發可以分為三種,正向端口轉發,反向端口轉發和動態端口轉發。為了演示這三種端口轉發方式的用法我們先假設存在有2個網域Office和Prod,在…

    Linux干貨 2015-02-09
  • 純文本配置還是注冊表

    我們知道Unix/Linux下的程序配置文件從來都是純文本的,你可以自由地修改和查看,他們也沒有什么什么XML之類的玩意(參看XML的這兩篇文章:一,二),這個最重要的Unix文化(參看Unix傳奇下篇)40多年來就這么沿續下來了。我很佩服Microsoft的創新能力,一會兒用INI,一會兒用注冊表,一會又是用XML,這就是Windows的編程中那“強大”的…

    Linux干貨 2016-08-15
  • 系統基礎之shell腳本編程詳解2

    shell腳本編程2:   在上節我們介紹了shell腳本編程,但只是介紹了基礎的內容,下面將為大家介紹shell的腳本的高級用法,判斷與循環.判斷分為兩種:if語句和case語句;循環分為三種:for語句,while語句,until語句,select語句 判斷語句:  在腳本的編寫中,我們要使用大量的數據和命令,但對于使用的數據,我們要…

    Linux干貨 2016-08-19
  • DHCP簡單闡述及配置實現方法

    DHCP是什么…… DHCP是Dynamic Host Configuration Protocol的縮寫,它是TCP/IP協議簇中的一種,主要是用來給網絡客戶機分配動態的IP地址。 其主要功能是: 用于內部網絡或網絡服務供應商自動分配IP地址給用戶 用于內部網絡管理員作為對所有電腦作中央管理的手段 直接點就是,這些被…

    Linux干貨 2016-12-05
  • 一年直接在于春

    day01

    2018-03-26
  • 第四周小結

    這周我們主要學習了寫腳本的簡單語法,寫了一些簡單的腳本,下面就由我來簡單介紹一下: 第一步使用文本編輯來創建腳本: 創建好后在里面寫想要運行的腳本即可,然后按Esc—wq退出保存即可。也可以按q不保存退出;q!不保存強制退出;wq!保存強制退出。 第二步運行腳本,給予執行權限,在命令行上指定腳本的相對路徑和絕對路徑 對了,當在腳本里輸入內容時,要Ese&#8…

    2017-08-06
欧美性久久久久