grep和正则表达式
1.grep:Global search REgular expression and Print out the file



格式:
grep [options] pattern file[...]







 grep -e 'cat' -e 'dog' file



2.正则表达式
由一类特殊字符及文本字符所编写的模式,其中有些字符(元字符)不表示字符字面意义,而表示控制或通配(wildzard)的功能
分类:
基本正则表达式:Basic Regular Expression
扩展正则表达式Extension Regular Expression
grep -E,egrep

下面讨论的都是基本正则表达式
元字符分类:字符匹配、匹配次数、位置锚定、分组

1)字符匹配
 .匹配任意单个字符

 
 


2)匹配次数:用在要指定次数的字符后面,用于指定前面字符或字符串(  \(\)扩起的部分 ),要出现的次数









 与之相对应的有一种懒惰模式(lazy):尽可能少的匹配字符
 做法,简而言之就是在匹配次数的符号后面加上?
 但是grep不支持,只有切换到Perl支持的正则表达式的模式下才能支持,很简单,就是加-P选项
 Perl支持的扩展的正则表达式,也就是匹配次数的字符不用加前面的转义符了,例如
 grep -P "a+?b" file
 
 
3)位置锚定:定位出现的位置



 
 





  4)分组和向后引用


        a)分组0对应整个正则表达式
        b)实际上组号分配过程是要从左向右扫描两遍的,第一遍只给未命名组分组分配组号(1 2 ...)
        第二遍只给命名组分配((?<name>exp)或(?'name'exp) 调用时用 \k<name>或\k'name' grep -P(PerlRE)支持这样做)
        


  
  5)断言(grep -P支持)


 (1)(?=exp),也叫零宽度正预测先行断言,
   格式:pattern1(?=pattern2) 
   匹配这样的字符串
   a)字符串本身匹配pattern1
   b)字符串后面的内容匹配pattern2
 
 
 grep -P "(\d{4}(?=:\d{4}:)):\1" /etc/passwd
 输出:
 redhat:x:1000:1000:redhat:/home/redhat:/bin/bash
user1:x:1001:1001::/home/user1:/bin/bash
user2:x:1002:1002::/home/user2:/bin/bash
user3:x:1003:1003::/home/user3:/bin/bash

 Attention:()可以加在pattern1(?=pattern2)整个外侧,也可以只加在pattern1外侧
 
 (2) (?<=exp),也叫零宽度正回顾后发断言
   格式:(?<=pattern2)pattern1 
   匹配这样的字符串
   a)字符串本身匹配pattern1
   b)字符串前面的内容匹配pattern2
   
   
   
   
   
user1:x:1001:1001::/home/user1:/bin/bash
user2:x:1002:1002::/home/user2:/bin/bash
user3:x:1003:1003::/home/user3:/bin/bash

Attention:()可以加在(?<=pattern2)pattern1整个外侧,也可以只加在pattern1外侧

2)负向零度断言

 格式:pattern1(?!(pattern2)) 
   匹配这样的字符串
   a)字符串本身匹配pattern1
   b)字符串后面的内容不匹配pattern2 
   Attention:但(?!(pattern2)) 有时可以放在前面,例如
   echo -e "abcdabc\n shxjah" | grep -P "(?!(abc))\w+"
   输出:
abcdabc
shxjah

(2)(?<!(exp)),零宽度负回顾后发断言
格式:(?!(pattern2)) pattern1


   
   
   例如:在/etc/passwd中找到gid是三位数的行
   综合零宽度负向预测先行断言和零宽度负回顾后发断言
   grep -P "(?<!(x:))\b\d{3}(?!(\d))" /etc/passwd
   输出:
games:x:12:100:games:/usr/games:/sbin/nologin
polkitd:x:999:999:User for polkitd:/:/sbin/nologin
colord:x:998:998:User for colord:/var/lib/colord:/sbin/nologin
usbmuxd:x:113:113:usbmuxd user:/:/sbin/nologin
rtkit:x:172:172:RealtimeKit:/proc:/sbin/nologin
qemu:x:107:107:qemu user:/:/sbin/nologin
chrony:x:997:995::/var/lib/chrony:/sbin/nologin
...

3.需要小心的陷阱
1)找出文件当中含有-v的行 (string start with dash )




  2)$的重要性
添加用户bash、testbash、basher以及nologin(其shell为/sbin/nologin),而后找出/etc/passwd文件中用户名与shell类型相同的行



4.经典的正则表达式
1)匹配IP地址
grep -Po "((25[0-5]|2[0-4]\d|[01]?\d\d?)\.)(25[0-5]|2[0-4]\d|[01]?\d\d?)" file
后面的...(25[0-5]|2[0-4]\d|[01]?\d\d?)一定要加上括号,否则会出现这样的情况...25[0-5]|2[0-4]\d|[01]?\d\d?,会分别匹配...25[0-5]和2[0-4]\d以及[01]?\d\d?,后两个没有...的部分


 

https://blog.51cto.com/bloodhero/1795314