grep, egrep及相应的正则表达式用法详解
一、grep/egrep
Global search REgular expression and Print out的简写,是一种强大的文本搜索工具,它根据用户指定的文本模式(正则表达元字符以及正常字符组合而成)对目标文件进行逐行搜索,并把匹配的行打印出来。Unix的grep家族包括grep、egrep和fgrep。
linux使用GNU版本的grep。它功能更强,可以通过-E、-F命令行选项来使用egrep和fgrep的功能(fgrep不使用正则表达式搜索)
[root@localhost tmp]# whatis grepgrep (1) - print lines matching a patterngrep (1p) - search a file for a pattern[root@localhost tmp]# 然后可以在这用 man grep 或者 man 1 grep 查询grep及正则表达式的用法
grep命令:
grep [OPTIONS] PATTERN [FILE...]
例子:grep --color=auto "root" /etc/passwd
[root@localhost ~]# alias grep='grep --color=auto'[root@localhost ~]# echo $? 0
匹配模式选择:
不选表示默认使用基本正则表达式
-E:使用扩展的正则表达式
-F:使用fgrep模式,PATERN不使用正则表达式
PATERN:使用这则表达式控制过滤条件,见本文后半段。
基本输出控制:
-c:只输出匹配行的计数
--color=[WHEN]:输出的匹配字段的颜色,WHEN=auto或neve或always
-l:查询多文件时只输出包含匹配字符的文件名。
输出行预设:
-H:--with-filename,搜索多个文件时可以用次选项在每行输出结果前显示对应的文件名
-h:查询多文件时输出结果不显示文件名,结果需要通过管道再处理时用到
-n:--line-number,输出匹配行并在行首显示其在源文件中的行号
内容行数控制(-o选项优先级高于本选项):
-A #:输出匹配行及其后面的#行
-B #: 输出匹配行加其前面的#行
-C #:输出匹配行及其前后各#行
文件及路径选择:
-R,-r:递归读取路径下的子目录及文件,相当于 -d recurse 选项
匹配控制:
-i: --ignore-case,不区分字符大小写-v:显示不包含匹配文本的所有行。
-w:–word-regexp精确匹配,匹配单词还不是字符串
二、正则表达式
参考阅读:
正则表达式30分钟教程
注:与Linux里的操作规则略有不同,但基本思想不变
正则表达式是对串操作的一种逻辑公式,就是用事先定义好的一些特定字符(元字符)、及这些特定字符的组合,组成一个“规则字符串”,这个“规则字符串”用来表达对字符串的一种过滤逻辑。其中的元字符不表示字符本身的意义,而是用于表达控制或通配等功能;
对象:字符串
组成:元字符+正常字符
功用:过滤文本字符,查找匹配字符并得出结果,供其它命令使用
作用对象:文本字符(文本文件里面的内容)
分类:结合grep
①基本正则表达式: grep
②扩展正则表达式: grep -E, egrep
③fgrep: fast grep, 不支持使用正则表达式
给定一个正则表达式和另一个字符串,我们可以达到如下的目的:
1. 给定的字符串是否符合正则表达式的过滤逻辑(称作“匹配”);
2. 可以通过正则表达式,从字符串中获取我们想要的特定部分。
正则表达式的特点是:
1. 灵活性、逻辑性和功能性非常的强;
2. 可以迅速地用极简单的方式达到字符串的复杂控制。
由于正则表达式主要是文本,因此它在各种场合都有应用,小到著名编辑器EditPlus,大到Microsoft Word、Visual Studio等大型编辑器,都可以使用正则表达式的强大过滤功用来处理文本内容。
基本正则表达式元字符:
⑴字符匹配:
. :匹配任意单个字符
[]: 匹配指定范围内的任意单个字符
[^]: 匹配指定范围外的任意单个字符
[0-9], [[:digit:]]所有数字字符中任取一;
[^0-9], [^[:digit:]]所有非数字字符中任取一
[a-z], [[:lower:]]所有小写字母字符中任取一
[A-Z], [[:upper:]]所有大些字母字符中取一
[[:space:]]空格字符(不是空白字符)
[[:punct:]]所有标点符号中任取一
[0-9a-zA-Z], [[:alnum:]]所有的数字和字母集合中任取一
[a-zA-Z], [[:alpha:]]所有的字母集合中任取一
[:graph:] 非空字符(非空格、控制字符)
[:cntrl:] 控制字符
⑵次数匹配:在期望匹配字符后面提供一个控制符,用于表达匹配其前面字符指定的次数
①* : 任意长度,表示0次、1次或多次;
"ab*c"
abbc, abc,ac √
abb ×
(PS: × -不匹配 √ -匹配 ,下同)
②.* 任意长度的任意字符
工作于贪婪模式
贪婪模式——当正则表达式中包含能接受重复的限定符时,通常的行为是(在使整个表达式能得到匹配的前提下)匹配尽可能多的字符。以这个表达式为例:a.*b,它将会匹配最长的以a开始,以b结束的字符串。如果用它来搜索aabab的话,它会匹配整个字符串aabab
③\?:0次或1次;表示其左侧字符可有可无
"ab\?c"
abbc, ×
ac, abc √
④\+: 1次或多次;表示其左侧字符至少出现1次;
"ab\+c"
ac, ×
abc, abbbbc √
⑤\{m\}:m次;表示其左侧字符精确出现m次;
⑥\{m,n\}:至少m次,至多n次;
ab\{2\}c
ac, abc, abbbc ×
abbc √
ab\{0,3\}c
ac,abc,abbc, abbbc √
abbbbbc ×
⑦\{0,n\}:至多n次;
⑧\{m,\}:至少m次;
⑶位置锚定:
①^: 锚定行首
^PATTERN
②$: 锚定行尾
PATTERN$
③^PATTERN$:用模式来匹配整行;
# grep "^[[:space:]]*$" /etc/rc.d/rc.sysinit
④^$: 匹配空白行;
⑷单词锚定:由非特殊字符组成的连续的字符串
①\< :锚定词首,也可用\b
\<PATTERN, 或\bPATTERN
# grep "\<sh" /etc/passwd
②\> :锚定词尾,也可以用\b
PATTERN\>, 或PATTERN\b
③\<PATTERN\>:匹配PATTERN能匹配到的整个单词
# ifconfig | grep "\<[0-9]\{2\}\>"
⑸分组:\( PATTERNS \)
注:PATTERNS 与两边必须各有一个隔开空格,否则报错
注意:分组中的模式,在某次的具体匹配过程中所匹配到的字符,可以被grep记忆(保存于内置的变量中,这些变量是\1, \2, ...),因此,还可以被引用;
\1: 引用,模式中自左而右,由第一个左括号以及与之对应的右括号中的模式所匹配到的内容;
\2: 引用 ,模式中自左右,由第二个左括号以及与之对应的右括号中的模式所匹配到的内容
\( ab\( cd \)mn \) \1 \2
abcdmnabcdmncd √
“\( a.b \).*\1"
amb hello anb ×
amb hello amb √
PS:\1 引用的是上次匹配到的结果,不是重新匹配一个合适过滤条件的字符过来
扩展的正则表达式元字符:
表达方式与基本正则表达式基本相同
⑴字符匹配:
. 匹配任意单个字符
[ ] 匹配指定范围内的任意单个字符
[^ ] 匹配指定范围外的任意单个字符
[0-9], [[:digit:]]所有数字字符中任取一;
[^0-9], [^[:digit:]]所有非数字字符中任取一
[a-z], [[:lower:]]所有小写字母字符中任取一
[A-Z], [[:upper:]]所有大些字母字符中取一
[[:space:]]空格字符(不是空白字符)
[[:punct:]]所有标点符号中任取一
[0-9a-zA-Z], [[:alnum:]]所有的数字和字母集合中任取一
[a-zA-Z], [[:alpha:]]所有的字母集合中任取一
[:graph:] 非空字符(非空格、控制字符)
[:cntrl:] 控制字符
⑵次数匹配:
*: 任意次
?:0或1次
+: 至少1次
{m}:精确匹配m次;
{m,n}:至少m次,至多n次;
{m,}:至少m次;
{0,n}:至多n次;
⑶位置锚定:
^ 锚定行首
$ 锚定行尾
\<, \b 锚定词首
\>, \b 锚定词尾
⑷分组:
( ) 以整体参与过滤匹配运算
引用:\1, \2, ... 引用匹配到的结果
⑸或者:
a|b:a或者b
或者两侧的所有内容;如果仅需要中竖线两侧的内容,则用分组括号括起即可。基本正则表达式没有这个功能。如
xy(z|a)bc 表示xyzbc或者xyabc
xyz|abc 表示xyz或者abc
正则表达式 | 扩展正则表达式 | 涵义 | |
字符匹配 | . | 匹配任意单个字符 | |
[ ] | 匹配指定范围内的任意单个字符 | ||
[^ ] | 匹配指定范围外的任意单个字符 | ||
[0-9],[[:digit:]] | 所有数字字符中任取一 | ||
[^0-9], [^[:digit:]] | 所有非数字字符中任取一 | ||
[a-z], [[:lower:]] | 所有小写字母字符中任取一 | ||
[A-Z], [[:upper:]] | 所有大些字母字符中取一 | ||
[[:space:]] | 空格字符(不是空白字符) | ||
[[:punct:]] | 所有标点符号中任取一 |
字符匹配 | [0-9a-zA-Z], [[:alnum:]] | 所有的数字和字母集合中任取一 | |
[a-zA-Z], [[:alpha:]] | 所有的字母集合中任取一 | ||
[:graph:] | 非空字符(非空格、控制字符) | ||
[:cntrl:] | 控制字符 | ||
次数匹配 | * .* 表示任意长度的任意字符 | 任意长度,表示0次、1次或多次 | |
\? | ? | 0次或1次;表示其左侧字符可有可无 | |
\+ | + | 1次或多次;表示其左侧字符至少出现1次 | |
\{m\} | {m} | m次;次数=m | |
\{m,n} | {m,n} | 至少m次,至多n次,m≦次数≦n | |
\{0,n} | {0,n} | 至多n次,0≦次数≦n |
次数匹配 | \{m,\} | {m,} | 至少m次,m≦次数 |
位置锚定 | ^ | 锚定行首 | |
$ | 锚定行尾 | ||
^PATERN$ | 用模式来匹配整行 | ||
^$ | 匹配空白行 | ||
单词锚定 | \<或者\b | 锚定词首 | |
\>或者\b | 锚定词尾 | ||
分组 | \( PATTERN \) \1,\2,… | ( PATTERNS ) \1,\2,… | 以整体参与过滤匹配运算,\1,\2,…表示引用 字符跟括号之间要有空格 |
或者 | 无此项 | a|b | a或者b |
练习:
参考网址:
进阶习题:
1、用正则表达式查找合理的ip
2、写出查找合理全国座机电话的正则表达式,区号和号码之间用“-”或“ ”相连