作为Linux上文本处理三剑客之一的文本搜索工具,grep和egrep是基于“pattern(模式)”对给定文本进行搜索操作。


正则表达式:

      即 Regular Expression 缩写为REGEX. 是由一类特殊字符及文本字符所编写的模式,其有些字符不表示其字面意义,而是用于表示控制或通配的功能。

  正则表达式分类:

     基本正则表达式:BRE (Basic Regular Expression)

     扩展正则表达式:ERE (Extend Regular Expression)


  正则表达式引擎:利用正则表达式模式分析给定文本的程序


grep家族:

                grep:支持使用基本正则表达式

      egrep:支持使用扩展正则表达式

        fgrep:不支持使用正则表达式

grep

  grep是Global search Regular Expression and Print out the line 的缩写,即根据用户指定的文本搜索模式“PATTERN”对目标文件进行逐行搜索并打印显示被模式匹配到的行或者匹配的字符串本身的一种文本搜索工具。所谓模式:即由文本字符及正则表达式元字符所编写的过滤条件。

   使用格式:grep [OPTION]... PATTERN [FILE]...

     其中PATTERN项需要最好使用单引号('')或者双引号("")扩起来,如果需要对模式进行转换,则需要使要使用双引号(""),如果不需要进行转换,则使用单引号或双引号都可以;模式还可以使用正则表达式来表示。

    常用选项之一:

      --color:用来指定被模式匹配到的字符的显示颜色,参数选项有never,always和auto

     grep和egrep命令及相应的正则表达式用法总结_第1张图片

         在Centos 7上,此命令别名是提前定义好的,因此使用的时候,可以不用加--color

     -v:反向匹配,即不能被模式所匹配到的行,也可以使用--invert-match长选项

     

     -i:不区分大小写,也可以使用--ignore-case长选项

     grep和egrep命令及相应的正则表达式用法总结_第2张图片

     -o:仅显示匹配到的文本自身;即只显示一行文本中被匹配到的文本自身

     

     -E:支持ERE(扩展的正则表达式),相当于egrep(下面会讲)

     -r: 连带文件夹以下目录也查找,即递归查找

     grep和egrep命令及相应的正则表达式用法总结_第3张图片

     -f, --file=FILE 从文件中读取正则表达式

     -q, --quiet, --silient:静默模式,不输出任何信息

     grep和egrep命令及相应的正则表达式用法总结_第4张图片

    注:如果正则表达式中有元字符,需要使用引号给括起来;单引号是强引用,双引号是弱引用;即模式中有变量应使用双引号;centos 7上命令别名中:grep='grep --color=auto',centos 6上没有此功能.

 基本正则表达式元字符:

   字符匹配:

       .:匹配任意单个字符;

       grep和egrep命令及相应的正则表达式用法总结_第5张图片

      [ ]:匹配范围内的任意单个字符;

       grep和egrep命令及相应的正则表达式用法总结_第6张图片

      [^ ]:匹配范围外的任意单个字符

       grep和egrep命令及相应的正则表达式用法总结_第7张图片

      [:digit:]:表示所有的数字,也可以使用[0-9]表示

        grep和egrep命令及相应的正则表达式用法总结_第8张图片

      [:lower:]:表示所有小写字母

        grep和egrep命令及相应的正则表达式用法总结_第9张图片

      [:upper:]:表示所有大写字母

        grep和egrep命令及相应的正则表达式用法总结_第10张图片

        [:alpha:]:表示所有字母,也可使用[a-z]表示

        grep和egrep命令及相应的正则表达式用法总结_第11张图片

        [:alnum:]:表示所有的数字和字母

        grep和egrep命令及相应的正则表达式用法总结_第12张图片

      [:space:]:表示空白字符

        grep和egrep命令及相应的正则表达式用法总结_第13张图片 

       [:blank:]:表示空格键和Tab按键两者

       grep和egrep命令及相应的正则表达式用法总结_第14张图片

      [:punct:]:表示所有特殊字符

        grep和egrep命令及相应的正则表达式用法总结_第15张图片

      注:使用# man 7 glob :可以查看Character classes and internationalization


   次数匹配:

     用在要指定其出现的次数的字符后面,用于限制其前面的字符要出现的次数;默认工作于贪婪模式

      贪婪模式:贪婪模式在整个表达式匹配成功的前提下,尽可能多的匹配,而非贪婪模式在整个表达式匹配成功的前提下,尽可能少的匹配非贪婪模式:只被部分NFA引擎所支持.


     *:匹配前面的字符任意次(0,1或多次)

     grep和egrep命令及相应的正则表达式用法总结_第16张图片

     .*:任意长度的任意字符

     grep和egrep命令及相应的正则表达式用法总结_第17张图片

     \+:匹配前面的字符至少1此

     grep和egrep命令及相应的正则表达式用法总结_第18张图片

     \?:匹配前面的0次或1次,即前面的字符可有可无

     grep和egrep命令及相应的正则表达式用法总结_第19张图片

     \{m\}:其前面的字符出现m次,m为非负整数

     

     \{m,n\}:其前面的字符出现m次,m为非负整数;[m,n]

          \{0,n\}:至多n次;

     

          \{m,\}:至少m次;

     grep和egrep命令及相应的正则表达式用法总结_第20张图片


       位置锚定:

         限制使用模式搜索文本,限制模式所匹配到的文本只能出现于目标文本的哪个位置

     ^:行首锚定;用于模式的最左侧,^PATTERN

     grep和egrep命令及相应的正则表达式用法总结_第21张图片

     $:行尾锚定;用于模式的最右侧,PATTERN$

     grep和egrep命令及相应的正则表达式用法总结_第22张图片

     ^PATTERN$:要让PATTERN完全匹配一整行

     grep和egrep命令及相应的正则表达式用法总结_第23张图片

     ^$:匹配空行

     grep和egrep命令及相应的正则表达式用法总结_第24张图片

     ^[[:space:]]*$ : 空行或者空白行

     grep和egrep命令及相应的正则表达式用法总结_第25张图片     


   单词锚定:

      \<或\b:词首锚定,用于单词模式的左侧,格式为\

      grep和egrep命令及相应的正则表达式用法总结_第26张图片

      \>或\b:词尾锚定,用于单词模式的右侧,格式为PATTERN\>, PATTERN\b

      grep和egrep命令及相应的正则表达式用法总结_第27张图片

      \:单词锚定

      grep和egrep命令及相应的正则表达式用法总结_第28张图片


     单词:所谓单词即由非特殊字符组成的连续字符(字符串)都称为单词

练习:

    1、显示/etc/passwd文件中不以bash结尾的行;

     # grep -v "bash$" /etc/passwd


     2、找出/etc/passwd文件中的三位或四位数;

     # grep "\<[0-9]\{3,4\}\>" /etc/passwd


     3、找出/etc/grub2.cfg文件中,以至少一个空白字符开头,后面又跟了非空白字符的行;

     # grep "^[[:space:]]\+[^[:space:]]" /etc/grub2.cfg


    4、找出"netstat  -tan”命令的结果中,以‘LISTEN’后跟0或多个空白字符结尾的行;

     # netstat -tan | grep "LISTEN[[:space:]]*$"


    5、找出"fdisk  -l“命令的结果中,包含以/dev/后跟sd或hd及一个小字母的行;

     # fdisk -l | grep "/dev/[sh]d[a-z]\>"


    6、找出”ldd  /usr/bin/cat“命令的结果中文件路径;

     # ldd /usr/bin/cat | grep -o "/[^[:space:]]\+"

 

   分组与引用:

     \(PATTERN\):将此PATTERN匹配到的字符当作一个不可分割的整体进行处理

     Note:分组括号中的模式匹配到的字符会被正则表达式引擎自动记录于内部的变量中,这些变量是\1, \2, \3, ...pat1\(pat2\)pat3\(pat4\(pat5\)pat6\)


      \n:模式中第n个左括号以及与之匹配的右括号之间的模式所匹配到的字符串;(不是模式,而是模式匹配的结果)


      \1:第一组括号中的pattern匹配到的字符串

      \2:第二组括号中的pattern匹配到的字符串


        一个很经典的示例:

      grep和egrep命令及相应的正则表达式用法总结_第29张图片

       以上此种方式称为后向引用:引用前面的括号中的模式所匹配到的字符串


  常用选项之二:

      -E, --extended-regexp:支持使用扩展正则表达式

      -F, --fixed-strings:支持使用固定字符串,不支持正则表达式,相当于fgrep

      -G, --basic-regexp:支持使用基本正则表达式;对fgrep和egrep管用

      -P, --perl-regexp:支持使用pcre正则表达式

      -e PATTERN, --regexp=PATTERN:多模式机制

      grep和egrep命令及相应的正则表达式用法总结_第30张图片

      -f FILE, --file=FILE:FILE为每行包含了一个pattern的文本文件,即grep script

      grep和egrep命令及相应的正则表达式用法总结_第31张图片

      -A NUM, --after-context=NUM : 显示匹配到内容的后NUM行

      grep和egrep命令及相应的正则表达式用法总结_第32张图片

      -B NUM, --before-context=NUM : 显示匹配到内容的前NUM行

      

      -C NUM, -NUM, --context=NUM : 显示匹配到内容的前后各NUM行

      grep和egrep命令及相应的正则表达式用法总结_第33张图片

      

egrep:

   支持使用扩展正则表达式的grep命令,相当于grep -E;

   使用格式:egrep [OPTIONS] PATTERN [FILE...]

    扩展正则表达式的元字符:

     字符匹配

        .:任意单个字符

        [ ]:范围内的任意单个字符

        [^ ]:范围外的任意单个字符

     匹配次数:

        *:表示其前的字符任意次

        grep和egrep命令及相应的正则表达式用法总结_第34张图片

        ?:表示其前的字符0次或1次;

        

        +:表示其前的字符1次或多次;

        grep和egrep命令及相应的正则表达式用法总结_第35张图片

        {m}:表示其前的字符匹配m次;

        

        {m,n}:表示其前的字符至少m次,至多n次;

        grep和egrep命令及相应的正则表达式用法总结_第36张图片

        {0,n}:至多n次;

        grep和egrep命令及相应的正则表达式用法总结_第37张图片

        {m,} : 至少m次;

        grep和egrep命令及相应的正则表达式用法总结_第38张图片

     位置锚定:

         ^:行首

         $:行尾

         \<, \b:词首

         \>, \b:词尾

     分组及引用:

        (pattern):分组,括号中的模式匹配到的字符会被记录于正则表达式引擎内

                  部的变量中;

           后向引用:\1, \2, ...

         或者:

           a|b:表示a或者b; 或者表示的是整个左侧和整个右侧;

             如:C|cat:表示C或cat

               (C|c)at:表示Cat或cat

练习:

   1、显示/etc/passwd文件中不以bash结尾的行;

     # egrep -v "bash$" /etc/passwd


   2、找出/etc/passwd文件中的三位或四位数;

    # egrep "\<[0-9]{3,4}\>" /etc/passwd


   3、找出/etc/grub2.cfg文件中,以至少一个空白字符开头,后面又跟了非空白字符的行;

    # egrep "^[[:space:]]+[^[:space:]]" /etc/grub2.cfg


   4、找出"netstat  -tan”命令的结果中,以‘LISTEN’后跟0或多个空白字符结尾的行;

    # netstat -tan | egrep "LISTEN[[:space:]]*$

   

   5、找出"fdisk  -l“命令的结果中,包含以/dev/后跟sd或hd及一个小字母的行;

    # fdisk -l | egrep "/dev/[sh]d[a-z]\>"


   6、找出”ldd  /usr/bin/cat“命令的结果中文件路径;

    # ldd /usr/bin/cat | egrep -o "/[^[:space:]]+"


   7、找出/proc/meminfo文件中,所有以大写或小写s开头的行;至少用三种方式实现;

    # egrep "^(s|S)" /tmp/meminfo

    # grep "^[sS]" /tmp/meminfo

    # grep -i "^s" /tmp/meminfo


   8、显示当前系统上root、centos或slackware用户的相关信息;

    # egrep "^(root|centos|slackware)\>" /etc/passwd


   9、echo输出一个绝对路径,使用egrep取出其基名;

    # echo /etc/passwd/ | egrep -o "[^/]+/?$"


   10、找出ifconfig命令结果中的1-255之间的整数;

    # ifconfig | egrep "\<([1-9]|[1-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])\>"


   11、添加用户bash、testbash、basher及nologin,要求前三个用户的默认shell为/bin/bash,nologin的默认shell为/sbin/nologin,而后找出其用户名与shell名相同的用户;

    # useradd -s /bin/bash bash

    # useradd -s /bin/bash basher

     # useradd -s /bin/bash testsh

     # useradd -s /sbin/nologin nologin

    # egrep "^([[a-z0-9]+)\>.*\>\1$" /etc/passwd