Linux三劍客老大 awk

鬼知道我爲何記得這些命令。——編程三分鐘linux

概述

awksed命令相似,只不過sed擅長取行,awk命令擅長取列。(根據瞭解awk是一種語言,不過咱們只關注他處理文本的功能,用的好的話幾乎能夠取代excel)
原理:通常是遍歷一個文件中的每一行,而後分別對文件的每一行進行處理
用法:c++

awk [可選的命令行選項] 'BEGIN{命令 } pattern{ 命令 } END{ 命令 }'  文件名
複製代碼

打印某幾列

$ echo 'I love you' | awk '{print $3 $2 $1}'
youloveI
複製代碼

咱們將字符串 I love you 經過管道傳遞給awk命令,至關於awk處理一個文件,該文件的內容就是I love you,默認經過空格做爲分隔符(無論列之間有多少個空格都將看成一個空格處理)I love you就分割成三列了。
假如分割符號爲.,能夠這樣用shell

$ echo '192.168.1.1' | awk -F "." '{print $2}'
168
複製代碼

條件過濾

咱們知道awk的用法是這樣的,那麼pattern部分怎麼用呢?編程

awk [可選的命令行選項] 'BEGIN{命令 } pattern{ 命令 } END{ 命令 }'  文件名

$ cat score.txt
tom 60 60 60
kitty 90 95 87
jack 72 84 99
$ awk '$2>=90{print $0}' score.txt
kitty 90 95 87
複製代碼

$2>=90 表示若是當前行的第2列的值大於90則處理當前行,不然不處理。說白了pattern部分是用來從文件中篩選出須要處理的行進行處理的,這部分是空的表明所有處理。pattern部分能夠是任何條件表達式的判斷結果,例如>,<,==,>=,<=,!=同時還可使用+,-,*,/運算與條件表達式相結合的複合表達式,邏輯 &&,||,!一樣也可使用進來。另外pattern部分還可使用 /正則/ 選擇須要處理的行。bash

判斷語句

判斷語句是寫在pattern{ 命令 }命令中的,他具有條件過濾同樣的做用,同時他也可讓輸出更豐富網絡

$ awk '{if($2>=90 )print $0}' score.txt
kitty 90 95 87
$ awk '{if($2>=90 )print $1,"優秀"; else print $1,"良好"}' score.txt
tom 良好
kitty 優秀
jack 良好
複製代碼

BEGIN 定義表頭

awk [可選的命令行選項] 'BEGIN{命令 } pattern{ 命令 } END{ 命令 }'  文件名
複製代碼

使用方法以下:函數

$ awk 'BEGIN{print "姓名 語文 數學 英語"}{printf "%-8s%-5d%-5d%-5d\n",$1,$2,$3,$4}' score.txt
姓名 語文數學英語
tom 60 60 60
kitty 90 95 87
jack 72 84 99
複製代碼

這裏要注意,我爲了輸出格式好看,作了左對齊的操做(%-8s左對齊,寬8位),printf用法和c++相似。
不只能夠用來定義表頭,還能夠作一些變量初始化的工做,例如ui

$ awk 'BEGIN{OFMT="%.2f";print 1.2567,12E-2}'
1.26 0.12
複製代碼

這裏OFMT是個內置變量,初始化數字輸出格式,保留小數點後兩位。spa

END 添加結尾符

和BEGIN用法相似命令行

$ echo ok | awk '{print $1}END{print "end"}'
ok
end
複製代碼

數據計算

這個地方我要放大招了!上面的知識點你都記住了嗎?

$ awk 'BEGIN{print "姓名 語文 數學 英語 總成績"; \ sum1=0;sum2=0;sum3=0;sumall=0} \ {printf "%5s%5d%5d%5d%5d\n",$1,$2,$3,$4,$2+$3+$4;\ sum1+=$2;sum2+=$3;sum3+=$4;sumall+=$2+$3+$4}\ END{printf "%5s%5d%5d%5d%5d\n","總成績",sum1,sum2,sum3,sumall}'\
 score.txt
姓名 語文 數學 英語 總成績
  tom 60 60 60 180
kitty 90 95 87 272
 jack 72 84 99 255
總成績 222 239 246 707
複製代碼

由於命令太長,末尾我用\符號換行了。。

  • BEGIN體裏我輸出了表頭,並給四個變量初始化0
  • pattern體裏我輸出了每一行,並累加運算
  • END體裏我輸出了總統計結果
    固然了,一個正常人在用linux命令的時候是不會輸入那麼多格式化符號來對齊的,因此新命令又來了
    column -t(鬼知道我爲何會記得這麼多亂七八糟的命令。)


有用的內置變量

NF:表示當前行有多少個字段,所以$NF就表明最後一個字段
NR:表示當前處理的是第幾行
FILENAME:當前文件名
OFMT:數字輸出的格式,默認爲%.6g。表示只打印小數點後6 位

$ awk -F ':' '{print NR ") " $1}' demo.txt
1) root
2) daemon
3) bin
4) sys
5) sync
複製代碼

內置函數

awk定義了不少內置函數,用awk來寫shell腳本卻是一個不錯的選擇,可是大多數咱們是用不上的,如下是經常使用函數

$ echo 1 2 | awk '{print $1+sqrt($2)}'

2.41421
複製代碼

隨機數,先設置種子再隨機

rand() 0 <= n < 1,srand([expr]) |將 rand 函數的種子值設置爲 Expr 參數的值,或若是省略 Expr 參數則使用某天的時間。

$ echo 1 | awk 'BEGIN{srand()}{print rand()}'

0.929885
複製代碼

字符串

系統經常使用

不經常使用算數:


推薦閱讀

(點擊標題可跳轉閱讀)

linux三劍客之老三grep

Linux三劍客老二sed

天天三分鐘玩轉Git(完結)

我偷偷挖了一條網絡隧道,差點被公司激活

若是有幫助別忘了分享給朋友哦~

相關文章
相關標籤/搜索