`
天梯梦
  • 浏览: 13747615 次
  • 性别: Icon_minigender_2
  • 来自: 洛杉矶
社区版块
存档分类
最新评论

Linux Shell常用技巧(四)

 
阅读更多

九.  awk实用功能:

    和sed一样,awk也是逐行扫描文件的,从第一行到最后一行,寻找匹配特定模板的行,并在这些行上运行“选择”动作。如果一个模板没有指定动作,这些匹配的行就被显示在屏幕上。如果一个动作没有模板,所有被动作指定的行都被处理。
    
   1.  awk的基本格式:
    /> awk 'pattern' filename
    /> awk '{action}' filename
    /> awk 'pattern {action}' filename
    
    具体应用方式分别见如下三个用例:
    /> cat employees
    Tom Jones         4424    5/12/66         543354
    Mary Adams      5346    11/4/63         28765
    Sally Chang       1654    7/22/54         650000
    Billy Black         1683    9/23/44         336500

    /> awk '/Mary/' employees   #打印所有包含模板Mary的行。
    Mary Adams      5346    11/4/63         28765

    #打印文件中的第一个字段,这个域在每一行的开始,缺省由空格或其它分隔符。
    /> awk '{print $1}' employees
    Tom
    Mary
    Sally
    Billy
    
    /> awk '/Sally/{print $1, $2}' employees #打印包含模板Sally的行的第一、第二个域字段。
    Sally Chang
    
    2.  awk的格式输出:
    awk中同时提供了print和printf两种打印输出的函数,其中print函数的参数可以是变量、数值或者字符串。字符串必须用双引号引用,参数 用逗号分隔。如果没有逗号,参数就串联在一起而无法区分。这里,逗号的作用与输出文件的分隔符的作用是一样的,只是后者是空格而已。下面给出基本的转码序 列:

转码 含义
\n 换行
\r 回车
\t 制表符


    /> date | awk '{print "Month: " $2 "\nYear: ", $6}'
    Month: Oct
    Year:  2011

    /> awk '/Sally/{print "\t\tHave a nice day, " $1,$2 "\!"}' employees
                    Have a nice day, Sally Chang!

    在打印数字的时候你也许想控制数字的格式,我们通常用printf来完成这个功能。awk的特殊变量OFMT也可以在使用print函数的时候,控制数字的打印格式。它的默认值是"%.6g"----小数点后面6位将被打印。
    /> awk 'BEGIN { OFMT="%.2f"; print 1.2456789, 12E-2}'
    1.25  0.12

    现在我们介绍一下功能更为强大的printf函数,其用法和c语言中printf基本相似。下面我们给出awk中printf的格式化说明符列表:

格式化说明符 功能 示例 结果
%c 打印单个ASCII字符。 printf("The character is %c.\n",x) The character is A.
%d 打印十进制数。 printf("The boy is %d years old.\n",y) The boy is 15 years old.
%e 打印用科学记数法表示的数。 printf("z is %e.\n",z) z is 2.3e+01.
%f 打印浮点数。 printf("z is %f.\n",z) z is 2.300000
%o 打印八进制数。 printf("y is %o.\n",y) y is 17.
%s 打印字符串。 printf("The name of the culprit is %s.\n",$1); The name of the culprit is Bob Smith.
%x 打印十六进制数。 printf("y is %x.\n",y) y is f.

    注:假设列表中的变脸值为x = A, y = 15, z = 2.3, $1 = "Bob Smith"

    /> echo "Linux" | awk '{printf "|%-15s|\n", $1}'  # %-15s表示保留15个字符的空间,同时左对齐。
    |Linux          |

    /> echo "Linux" | awk '{printf "|%15s|\n", $1}'   # %-15s表示保留15个字符的空间,同时右对齐。
    |          Linux|

    #%8d表示数字右对齐,保留8个字符的空间。
     /> awk '{printf "The name is %-15s ID is %8d\n", $1,$3}' employees
    The name is Tom             ID is     4424
    The name is Mary            ID is     5346
    The name is Sally            ID is     1654
    The name is Billy             ID is     1683

    3.  awk中的记录和域:
    awk中默认的记录分隔符是回车,保存在其内建变量ORS和RS中。$0变量是指整条记录。
    /> awk '{print $0}' employees #这等同于print的默认行为。
    Tom Jones        4424    5/12/66         543354
    Mary Adams      5346    11/4/63         28765
    Sally Chang       1654    7/22/54         650000
    Billy Black         1683    9/23/44         336500

    变量NR(Number of Record),记录每条记录的编号。
    /> awk '{print NR, $0}' employees
    1 Tom Jones        4424    5/12/66         543354
    2 Mary Adams      5346    11/4/63         28765
    3 Sally Chang       1654    7/22/54         650000
    4 Billy Black         1683    9/23/44         336500

    变量NF(Number of Field),记录当前记录有多少域。
    /> awk '{print $0,NF}' employees
    Tom Jones        4424    5/12/66          543354   5
    Mary Adams      5346    11/4/63         28765     5
    Sally Chang      1654    7/22/54          650000   5
    Billy Black        1683     9/23/44         336500    5

    #根据employees生成employees2。sed的用法可以参考上一篇blog。
    /> sed 's/[[:space:]]\+\([0-9]\)/:\1/g;w employees2' employees
    /> cat employees
    Tom Jones:4424:5/12/66:543354
    Mary Adams:5346:11/4/63:28765
    Sally Chang:1654:7/22/54:650000
    Billy Black:1683:9/23/44:336500

    /> awk -F: '/Tom Jones/{print $1,$2}' employees2  #这里-F选项后面的字符表示分隔符。
    Tom Jones 4424

    变量OFS(Output Field Seperator)表示输出字段间的分隔符,缺省是空格。
    />  awk -F: '{OFS = "?"};  /Tom/{print $1,$2 }' employees2 #在输出时,域字段间的分隔符已经是?(问号)了
    Tom Jones?4424

    对于awk而言,其模式部分将控制这动作部分的输入,只有符合模式条件的记录才可以交由动作部分基础处理,而模式部分不仅可以写成正则表达式(如上面的例子),awk还支持条件表达式,如:
    /> awk '$3 < 4000 {print}' employees
    Sally Chang     1654    7/22/54         650000
    Billy Black       1683    9/23/44         336500

    在花括号内,用分号分隔的语句称为动作。如果模式在动作前面,模式将决定什么时候发出动作。动作可以是一个语句或是一组语句。语句之间用分号分隔,也可以用换行符,如:
    pattern { action statement; action statement; etc. } or
    pattern {
        action statement
        action statement
    }
    模式和动作一般是捆绑在一起的。需要注意的是,动作是花括号内的语句。模式控制的动作是从第一个左花括号开始到第一个右花括号结束,如下:
    /> awk '$3 < 4000 && /Sally/ {print}' employees
    Sally Chang     1654    7/22/54         650000

    4.  匹配操作符:
    " ~ " 用来在记录或者域内匹配正则表达式。
    /> awk '$1 ~ /[Bb]ill/' employees      #显示所有第一个域匹配Bill或bill的行。
    Billy Black     1683    9/23/44         336500

    /> awk '$1 !~ /[Bb]ill/' employees     #显示所有第一个域不匹配Bill或bill的行,其中!~表示不匹配的意思。
    Tom Jones        4424    5/12/66         543354
    Mary Adams      5346    11/4/63         28765
    Sally Chang       1654    7/22/54         650000

    5.  awk的基本应用实例:
    /> cat testfile
    northwest     NW        Charles Main            3.0        .98        3        34
    western        WE        Sharon Gray            5.3        .97        5        23
    southwest     SW        Lewis Dalsass          2.7        .8          2        18
    southern       SO        Suan Chin                5.1        .95        4        15
    southeast      SE        Patricia Hemenway    4.0        .7          4        17
    eastern         EA        TB Savage                4.4        .84        5        20
    northeast      NE        AM Main Jr.               5.1        .94        3        13
    north            NO        Margot Weber          4.5        .89        5        9
    central          CT        Ann Stephens           5.7        .94        5        13

    /> awk '/^north/' testfile            #打印所有以north开头的行。
    northwest      NW      Charles Main     3.0     .98     3       34
    northeast       NE      AM Main Jr.        5.1     .94     3       13
    north             NO      Margot Weber   4.5     .89     5       9

    /> awk '/^(no|so)/' testfile          #打印所有以so和no开头的行。
    northwest       NW      Charles Main                3.0     .98      3       34
    southwest       SW      Lewis Dalsass              2.7     .8       2       18
    southern         SO      Suan Chin                    5.1     .95     4       15
    southeast        SE      Patricia Hemenway        4.0     .7       4       17
    northeast        NE      AM Main Jr.                   5.1     .94     3       13
    north              NO      Margot Weber              4.5     .89     5       9

    /> awk '$5 ~ /\.[7-9]+/' testfile     #第五个域字段匹配包含.(点),后面是7-9的数字。
    southwest       SW      Lewis Dalsass            2.7     .8      2       18
    central             CT      Ann Stephens            5.7     .94     5       13

    /> awk '$8 ~ /[0-9][0-9]$/{print $8}' testfile  #第八个域以两个数字结束的打印。
    34
    23
    18
    15
    17
    20
    13

十.  awk表达式功能:

    1.  比较表达式:
    比较表达式匹配那些只在条件为真时才运行的行。这些表达式利用关系运算符来比较数字和字符串。见如下awk支持的条件表达式列表:

运算符 含义 例子
< 小于 x < y
<= 小于等于 x <= y
== 等于 x == y
!= 不等于 x != y
>= 大于等于 x >= y
> 大于 x > y
~ 匹配 x ~ /y/
!~ 不匹配 x !~ /y/

    /> cat employees
    Tom Jones        4424    5/12/66         543354
    Mary Adams      5346    11/4/63         28765
    Sally Chang       1654    7/22/54         650000
    Billy Black         1683    9/23/44         336500

    /> awk '$3 == 5346' employees       #打印第三个域等于5346的行。
    Mary Adams      5346    11/4/63         28765

    /> awk '$3 > 5000 {print $1}' employees  #打印第三个域大于5000的行的第一个域字段。
    Mary

    /> awk '$2 ~ /Adam/' employess      #打印第二个域匹配Adam的行。
    Mary Adams      5346    11/4/63         28765

    2.  条件表达式:
    条件表达式使用两个符号--问号和冒号给表达式赋值: conditional expression1 ? expression2 : expressional3,其逻辑等同于C语言中的条件表达式。其对应的if/else语句如下:
    {
        if (expression1)
            expression2
        else
            expression3
    }
    /> cat testfile
    northwest     NW        Charles Main             3.0        .98        3        34
    western        WE        Sharon Gray             5.3        .97         5        23
    southwest     SW        Lewis Dalsass           2.7        .8          2        18
    southern       SO        Suan Chin                 5.1        .95        4        15
    southeast      SE        Patricia Hemenway     4.0        .7          4        17
    eastern         EA        TB Savage                 4.4        .84        5        20
    northeast      NE        AM Main Jr.                5.1       .94         3        13
    north            NO        Margot Weber           4.5       .89         5        9
    central          CT        Ann Stephens            5.7       .94         5        13

    /> awk 'NR <= 3 {print ($7 > 4 ? "high "$7 : "low "$7) }' testfile
    low 3
    high 5
    low 2

    3.  数学表达式:
    运算可以在模式内进行,其中awk将所有的运算都视为浮点运算,见如下列表:

运算符 含义 例子
+ x + y
- x - y
* x * y
/ x / y
% 取余 x % y
^ 乘方 x ^ y

    /> awk '/southern/{print $5 + 10}' testfile  #如果记录包含正则表达式southern,第五个域就加10并打印。
    15.1

    /> awk '/southern/{print $8 /2 }' testfile   #如果记录包含正则表达式southern,第八个域除以2并打印。
    7.5

    4.  逻辑表达式:
    见如下列表:

运算符 含义 例子
&& 逻辑与 a && b
|| 逻辑或 a || b
! 逻辑非 !a

    /> awk '$8 > 10 && $8 < 17' testfile   #打印出第八个域的值大于10小于17的记录。
    southern        SO      Suan Chin               5.1     .95     4       15
    central            CT      Ann Stephens         5.7     .94     5       13

    #打印第二个域等于NW,或者第一个域匹配south的行的第一、第二个域。
    /> awk '$2 == "NW" || $1 ~ /south/ {print $1,$2}' testfile
    northwest  NW
    southwest  SW
    southern    SO
    southeast   SE

    /> awk '!($8 > 13) {print $8}' testfile  #打印第八个域字段不大于13的行的第八个域。
    3
    9
    13

    5.  范围模板:
    范围模板匹配从第一个模板的第一次出现到第二个模板的第一次出现,第一个模板的下一次出现到第一个模板的下一次出现等等。如果第一个模板匹配而第二个模板没有出现,awk就显示到文件末尾的所有行。
    /> awk '/^western/,/^eastern/ {print $1}' testfile #打印以western开头到eastern开头的记录的第一个域。
    western    WE
    southwest SW
    southern   SO
    southeast  SE
    eastern      EA    

    6.  赋值符号:
    #找到第三个域等于Ann的记录,然后给该域重新赋值为Christian,之后再打印输出该记录。
    /> awk '$3 == "Ann" { $3 = "Christian"; print}' testfile
    central CT Christian Stephens 5.7 .94 5 13

    /> awk '/Ann/{$8 += 12; print $8}' testfile #找到包含Ann的记录,并将该条记录的第八个域的值+=12,最后再打印输出。
    25

 

原文:Linux Shell常用技巧(四)

分享到:
评论

相关推荐

    Linux Shell常用技巧

    ### Linux Shell 常用技巧详解 在 Linux 系统中,Shell 是用户与操作系统交互的主要方式之一。本文将深入探讨几个常用的 Shell 技巧及其应用场景。 #### 1. 使用 `/dev/null` 和 `/dev/tty` 在 Linux 系统中,`/...

    Linux Shell常用技巧-带完整书签目录超清文字版.pdf

    本资源提供了“Linux Shell常用技巧-带完整书签目录超清文字版.pdf”,这是一个详细介绍了各种Linux Shell操作技巧的文档,包含了完整的书签目录,方便用户快速定位和学习。以下是基于该文档可能涵盖的一些核心知识...

    linux_shell实例精解

    Linux Shell是Linux操作系统中的一种命令解释器,它提供了一个用户与操作系统内核交互的界面,使得用户可以通过文本命令行执行各种操作。Shell脚本则是一种编程语言,它允许用户编写包含一系列命令的程序,实现自动...

    维护常用linux命令\shell技巧

    以下是一些关于“维护常用Linux命令\Shell技巧”的详细知识点: 1. **基本命令操作**: - `ls`:列出目录内容。 - `cd`:切换目录。 - `pwd`:显示当前工作目录。 - `mkdir`:创建新目录。 - `rm`:删除文件或...

    linux常用命令以及shell脚本

    linux常用命令以及shell脚本,常用技巧的使用

    linux shell 编程经典 教程

    通过学习《LINUX与UNIX SHELL编程指南》这本书,你将能够熟练掌握Linux Shell编程技巧,利用这些技能实现日常系统维护、自动化任务处理,甚至开发复杂的系统管理工具。在阅读过程中,结合实践操作,将理论知识转化为...

    Linux+Shell命令行及脚本编程实例详解-刘艳涛.mobi kindle版

    主要内容包括:Linux及Linux Shell简介、初识Linux Shell、常用Shell(Bash)命令、Shell命令进阶、Shell编程基础、Shell的条件执行、Bash循环、Shell函数、正则表达式、脚本输入处理、Shell重定向、管道和过滤器、...

    Linuxshell编写demo

    本文将深入探讨Linux Shell编写的基础知识,包括基本概念、常用命令、变量与参数、流程控制以及函数的使用。 首先,Shell是一个命令解释器,它接收用户输入的命令并执行。在Linux系统中,常见的Shell有Bash(Bourne...

    linux shell编程手册

    通过阅读"Linux Shell编程手册",初学者不仅能掌握Shell的基础用法,还能了解到更多高级特性和实践技巧,从而更好地利用Shell提升日常Linux系统管理的效率。同时,熟悉Shell编程也是成为一名合格Linux系统管理员的...

    LINUX SHELL 脚本攻略

    Linux系统中常用的Shell类型有多种,例如bash、ksh、csh、zsh等,不同的Shell有不同的语法和特性。Bash(Bourne Again SHell)是Linux系统中最普遍使用的Shell,本书应该也会重点介绍bash Shell脚本的编写技巧。 ...

    linux shell

    在Linux世界里,bash(Bourne-Again SHell)是最常用的Shell,但还有其他如sh、csh、ksh和zsh等。 一、Shell基础 1. 命令行界面:Shell主要工作在命令行界面,用户通过键盘输入命令,Shell解析这些命令并执行相应的...

    linux_shell从初学到精通

    本教程“Linux Shell从初学到精通”旨在引导初学者逐步掌握Shell编程的基本概念和高级技巧。 首先,我们从基础开始。在Linux环境中,Shell提供了命令行界面,用户可以通过输入命令来执行各种操作。学习Shell的第一...

    Linux Shell 参考文档

    通过阅读和理解这个“Linux Shell 参考文档”,你可以掌握Linux Shell的基本操作和脚本编程技巧,提升你在Linux环境下的工作能力。无论是日常系统管理还是自动化任务,熟练掌握Shell都是必不可少的技能。文档中的...

    Linux shell 脚本攻略

    本书《Linux Shell脚本攻略》(第2版)深入浅出地介绍了Shell脚本的编写技巧和实战应用,非常适合对Linux感兴趣的初学者学习。 **Shell脚本基础** 1. **Shell介绍**:Shell是Linux的命令解释器,它提供了一个与...

    linuxshell.rar帮助文档 简单实用

    这份“linuxshell.rar帮助文档”旨在提供关于Linux Shell的基础知识和实用技巧,帮助用户提高在终端中的操作效率。 一、Shell简介 Linux Shell是Linux系统中的一个核心组件,常见的有Bash(Bourne Again SHell)、...

    2本linux shell 编程chm

    在Linux环境中,Bash(Bourne-Again SHell)是最常用的Shell,也是许多Linux发行版的默认Shell。本文将深入探讨这两个CHM文件——"shell 命令合集.chm"和"高级bash脚本编程指南.CHM"所涵盖的Linux Shell编程相关知识...

    Linux shell 脚本攻略源代码第二版

    Shell脚本的基础在于Bash(Bourne-Again SHell),它是Linux系统中最常用的Shell。Bash提供了许多内置命令、控制结构和变量,使得编写脚本变得简单而强大。例如,你可以使用`echo`命令打印文本,`if`语句进行条件...

    Linux常用命令 shell 常用命令

    ### Linux常用命令详解 Linux作为一款强大的开源操作系统,其核心优势之一在于丰富的命令行工具,这些工具能够高效地完成各种...随着对Linux的深入理解和实践,你将发现更多有用的命令和技巧,不断扩展自己的技能树。

Global site tag (gtag.js) - Google Analytics