Linux上文本处理三剑客之grep

grep :文本过滤(模式:pattern)工具


    grep ,egrep ,fgrep(不支持正则表达式搜索)

grep:Global search REgular expression and Print out the line 


用途:文本搜索工具,根据用户指定的模式对目标文本逐行进行匹配检查,打印匹配到的行,

模式:由正则表达式字符及文本字符所编写的过滤条件

命令格式:

Usage: grep [OPTION]… PATTERN [FILE]…

OPTION:

  •     –color=auto 对匹配到地文本着色显示

  •     -v 显示不能够被pattern匹配到的行

  •     -i 忽略字符大小写

  •     -n 显示匹配到地行号 

  •     -c 统计匹配到的行数

  •     -o 仅显示匹配到的字符串

  •     -q 静默模式,不输出任何信息

  •     -A # after,后#行

  •     -B # before,前#行

  •     -C #  context,前后各#行

  •     -e 实现多个选项间地逻辑or关系 grep -e  'cat' -e 'dog' file

  •     -w 整行匹配整个单词

  •     -E 使用ERE,相当于egrep


正则表达式

REGEXP: 由一类特殊字符及文本字符所编写的模式,其中有些字符(元字符)不表示字符表面意义,而表示控制或通配的功能

程序支持:grep,vim,less,nginx等

表达式分两类:

    基本正则表达式:BRE

    扩展正则表达式:ERE

正则表达式引擎:

    采用不同的算法,检查处理正则表达式的软件模块

    PCRE (Per Compatible Regular Expressions)

元字符分类:字符匹配,匹配字数,位置锚定,分组

可以通过man命令查看 man 7 regex



字符匹配:

  •     . 匹配任意单个字符

  •     [] 匹配指定范围内的任意单个字符

  •     [^] 匹配指定范围外的任意单个字符

  •     [:digit:] 数字

  •     [:lower:] 小写字母

  •     [:upper:] 大写字母

  •     [:alpha:] 大小写字母

  •     [:alnum:] 字母和数字

  •     [:punct:] 符号

  •     [:space:] 空格



匹配次数:

  主要用在要指定次数的字符后面,用于指定前面的字符要出现的次数

  •     *    匹配前面的字符任意次,包括0次。贪婪模式,尽可能长的匹配

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

  •     \?   匹配其前面的字符0或1次

  •     \+   匹配其前面的字符至少1次

  •     \{m\} 匹配前面的字符m次

  •     \{m,n\} 匹配前面的字符至少m次,至多n次

  •     \{,n\} 匹配前面的字符至多n次

  •     \{m,\} 匹配前面的字符至少m次



位置锚定:

  主要用于定位出现的位置

  •     ^  行首锚定,用于模式的最左侧

  •     $  行尾锚定,用于模式的最右侧

  •     ^PATTERN$ 用于模式匹配整行

         ^$ 空行

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

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

  •     \> 或 \b 词尾锚定,用于单词模式的右侧

  •     \<PATTERN\> 匹配整个单词


分组:

  \(\) 将一个或多个字符捆绑在一起,当作一个整体进行处理,如:\(root\)\+

  分组括号中的模式匹配到的内容会被正则表达式引擎记录于内部的变量中,这些变量的命名方式为:\1,\2,\3,…

  \1:从左侧起,第一个左括号以及与之匹配右括号之间的模式所匹配到的字符

    比如:\(string1\+\(string2\)*\)

        \1 :string1\+\(string2\)*

        \2 :string2

    后向引用:引用前面的分组括号中的模式所匹配字符(而非模式本身)


把以上元字符极其含义总结如图

元字符 定义
^ 匹配行首
$ 匹配行尾
. 任意单一字符
[] []内任意单一字符
[^] 除[]内任意单一字符
* *前面字符重复不确定次数
\+ \+前面字符重复一次以上不确定次数
\? ?前面字符重复0或1次
\ 转义字符
.* 任意长度字符
\{n\} 前面字符重复n次
\{n,\} 前面字符重复n次以上
\{m,n\} 前面字符重复m次和n次之间
[:alpha:] 所有字母,包括大小写
[:alnum:] 所有字母和数字
[:upper:] 所有大写字母
[:lower:] 所有小写字母
[:digit:] 所有数字
[:punct:] 所有标点符号
[:space:] 空格和Tab


实战练习:

    

1、显示/proc/meminfo文件中以大小s开头的行;(要求:使 用两种方式) 

grep "^[sS].*" /proc/meminfo

grep  -e "^[S].*" -e "^[s].*" /proc/meminfo

blob.png

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

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

3、显示用户rpc默认的shell程序 

grep "^\brpc\b.*" /etc/passwd | cut -d: -f7

blob.png

4、找出/etc/passwd中的两位或三位数 

grep "\b[[:digit:]]\{2,3\}\b" /etc/passwd 

blob.png

加上-o选项可以只显示数字

5、显示/etc/grub2.cfg文件中,至少以一个空白字符开头的 且后面存非空白字符的行 

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

blob.png

6、找出"netstat -tan"命令的结果中以'LISTEN'后跟0、1 或多个空白字符结尾的行 

netstat -tan | grep "\<LISTEN\>[[:space:]]*$"

netstat -tan | grep "\<LISTEN\>[[:space:]]\{0,\}$"

blob.png

7、添加用户bash、testbash、basher以及nologin(其shell为 /sbin/nologin),而后找出/etc/passwd文件中用户名同shell名 的行

grep "\(^\b[[:alnum:]]\+\b\).*\1$" /etc/passwd

cat /etc/passwd | grep "\(^[[:alnum:]]\+\):.*\1$"

blob.png


egrep及扩展的正则表达式

egrep =grep -E

Usage: egrep [OPTION]… PATTERN [FILE]…

扩展正则表达式的元字符


字符匹配:

    . 任意单个字符

    [] 指定范围的字符

    [^] 不在指定范围内的字符


次数匹配:

    * 匹配前面字符任意次

    ? 0或1次

    + 1次或多次

    {m} 匹配m次

    {m,n} 匹配至少m,至多n次


位置锚定:

    ^ 行首

    $ 行尾

    \<或\b 词首

    \>或\b 词尾

分组:

    () 后向引用\1,\2


或者:

    a|b

    C|cat C或者cat

    (C|c)at Cat或者cat

实战练习:

1、显示当前系统root、mage或wang用户的UID和默认shell 

egrep "^\b(root|mage|wang)\b" /etc/passwd | cut -d: -f3,7

blob.png

2、找出/etc/rc.d/init.d/functions文件中行首为某单词(包 括下划线)后面跟一个小括号的行 

egrep "\b^([[:alpha:]]|_)+\b\(" /etc/rc.d/init.d/functions

blob.png

3、使用egrep取出/etc/rc.d/init.d/functions中其基名 

echo "/etc/rc.d/init.d/functions" |egrep '[^/]+(|/)$' -o

blob.png

4、使用egrep取出上面路径的目录名 

echo "/etc/rc.d/init.d/functions" | egrep "^.*/"

blob.png

5、统计以cent身份登录的每个远程主机IP地址的登录次数 

w | grep "^\bcent\b" |tr -s ' ' |cut -d " " -f3|sort -n|uniq -c

blob.png

6、利用扩展正则表达式分别表示0-9、10-99、100-199、 200-249、250-255 

7、显示ifconfig命令结果中所有IPv4地址

ifconfig |egrep "\b([[:digit:]].|[1-9][[:digit:]].|[1-2][[:digit:]]{2}.|[2][0-4][[:digit:]].|[25][0-5].){3}([[:digit:]]|[1-9][[:digit:]]|[1-2][[:digit:]]{2}|[2][0-4][[:digit:]]|[25][0-5])\b" 

blob.png

blob.png

类似文章