1.re模块
这个模块提供了类似于perl中的正则表达式匹配操作。匹配模型(pattern)和待匹配的字符串(string)可以是Unicode字符串或者ANSI字符串。
正则表达式用反斜杠(‘\’)来表示特定格式或者用来允许我们使用特殊字符的一般意义。这与python中字符串的用法相冲突,它们用了相同的策略,都是用转移字符'\'。
如:
python字符串 “\\\\"实际表示"\\",例如:
>print "\\\\"
>\\
则“\\\\"实际表示“\\”,而“\\”作为pattern string的时候则表示“\”
解决方法是为正则表达式使用python的raw string标记'r',以’r'作为前缀的字符串字面值不会以特殊的方式处理反斜杠(‘\’)。所以r"\n"是一个包含‘\’和‘n’两个字符的字符串,而”\n“则是一个单独的换行字符。通常在Python代码中,几乎所有的pattern都会用到这个raw string标记(‘r')。如:
python字符串 r“\\\\"实际表示"\\\\",例如:
>print r"\\\\"
>\\\\
而“\\\\”作为pattern string的时候则表示“\\”
注意到正则表达式可以用作模块re的函数方法。这些函数是一种捷径,不要求你编译正则表达式对象,但是缺少一些小的调整参数。
2.语法
一个正则表达式(RE)就指定了一系列可以与之匹配的字符串。这个re模块中的函数能够让你检查一个特定的字符串是否与一个给定的正则表达式相匹配。
多个正则表达式可以被串连起来形成一个新的正则表达式。如果A和B都是正则表达式,那么AB同样也是正则表达式。一般地,如果字符串p与A匹配,字符串q与B匹配,那么字符串pq与AB匹配。除非A或B有低的优先级,或者A,B间有其他边界条件,或者有指定序列的参考分组,否则以上这种串连方式都是试用的。因此,复杂的正则表达式可以很容易的由简单的原始的表达式构建起来。
下面简要的介绍一下正则表达式的格式,更多信息请参考。。。
正则表达式可以包含特殊和普通的字符。大多数不同字符是最简单的正则表达式,如'A','a','0'等,它们简单地匹配其自身。你可以将其串连起来,所以匹配模型last就匹配字符串‘last’。
像’|‘或’(‘字符属于特殊字符,它们可以代表某种普通的字符,或者影响它们周围的字符该如何被正则表达式所解释。我们无法在pattern string中包含null字符(因为无法用键盘输入,也无法用屏幕显示),但是我们可以用\number 记号来表示,如,’\x00‘。
这些特殊字符有:
’.‘
匹配任意字符,除了换行符。当re.DOTALL标记被指定时,则可以匹配包括换行符的任意字符。
’^‘
匹配字符串的开头,并且当re.MULTILINE标记被指定时,同样可以匹配紧挨着换行符的下一个字符。
如:在一般模式下,^foo.仅仅匹配’foo1\nfoo2\n‘中的'foo1'。而在MULTILINE模式下,则匹配'foo1'和'foo2'
’$‘
匹配字符串的末尾。在MULTILINE模式下,可以匹配换行符的前一个字符。
如:在一般模式下,foo.$仅仅匹配’foo1\nfoo2\n‘中的'foo2'。而在MULTILINE模式下,则匹配'foo1'和'foo2' ,在MULTILINE中$匹配’foo\n‘中的两个位置(empty):一个是在’\n‘前,一个在字符串的结尾。
'*'
合成的RE(*和前一个RE串连起来组成的RE,我们先叫它叫合成的RE)匹配0次或任意次前一个RE。如ab*可以匹配'a','ab','abb',或者a后边跟任意个b。
’+‘
合成的RE(*和前一个RE串连起来组成的RE,我们先叫它叫合成的RE)匹配1次或任意次前一个RE
’?‘
合成的RE(*和前一个RE串连起来组成的RE,我们先叫它叫合成的RE)匹配0次或1次前一个RE。
*?,+?,??
'*','+'和'?'修饰符都是贪婪的,它们会尽量多的匹配字符串。有时这种行为不是我们想要的。如果用正则表达式<*.>去匹配'<h1>title<H1>',则会匹配整个字符串,而不是'<H1>’。在修饰符后加'?'使其匹配非贪婪的或最小的匹配样式。如<.*?>匹配原字符串中的'<H1>’。
{m}
指定准确的m次前一RE匹配,如a{6}匹配‘aaaaaa’
{m,n}
使合成的RE匹配m到n次前一个RE,首先尝试匹配最多的次数。如a{2,5}匹配‘aaaaaa’中的5个a,而非2个、3个或4个a。忽略m,则下界为0,如a{,4}匹配0到4次a;忽略n,则上界为无穷大,如a{2,}匹配2到无穷次a。
{m,n}?
使合成的RE匹配m到n次前一个RE,首先尝试匹配最少的次数。如a{2,5}匹配‘aaaaaa’中的aa,aa,aa
'\'
逃逸字符(允许你匹配特殊字符,如*,?等)
[]
用来表示一组字符
单独列出:[amk] 匹配 ‘a','m'或'k'
列出范围:[a-z] 匹配 'a'到'z'中的任意字符
特殊字符在[]中失去特殊意义:[(?+*)] 匹配 '(','?','+','*'或')'
不在[]中的字符:[^abc] 匹配除了a,b,c之外的字符。[^^]匹配除了^之外的所有字符,^不在第一个位置上时没有特殊含义
'|'
A和B可以是任意的RE,A|B匹配A或者B,可以用这种方式分割任意数量的RE,随着目标字符串被扫描,会自动从左向右尝试匹配RE,一旦A匹配了,B就不再检测了。
如果想要匹配字符|,可以用 \|,或者[|]。
(...)
匹配在括号中的任意正则表达式,表示一个group的开始和结尾。一个group中的内容可以被重复利用,可以在随后的字符串中用\number 特殊序列进行匹配,其中\number从1开始对前面的()进行编号。
如:(.+) \1注意')'后面有空格。(abc)(bcd) \1
(?...)
是一个扩展标记,该表达式无任何意义,?后面跟的第一个字符决定了将来构建起的意义。扩展一般不建立新的group,(?P<name>...)除外。
(?iLmsux)
这个group自身匹配一个空串,它为后面的整个字符串设置了标志,这些字符i,L,m,s,u,x标志分别对应re.I(ignore case)、re.L(locale dependent)、re.M(multi-line)、re.S(dot matches all)、re.U(unicode dependent)、re.X(verbose)。免去了在re.compile()中添加额外的参数,而是直接将标志写进正则表达式了。
(?:...)
非捕获的group,不能在后续的表达式中被\number重复利用了
(?P<name>...)
与(...)一样,只不过在后续引用中可以用(?P=name)来重复利用,但仍可以用\number来引用,只不过多了一种方式。
(?P=name)
如上描述
(?#...)
是注释。被忽略
(?=...)
lookahead assertion
abc(?=def):先在字符串中找到abc,然后检测其后边是否是与def(也可以是其他RE表达式)匹配,若匹配则该abc符合要求
(?!...)
negative lookahead assertion
abc(?!def):先在字符串中找到abc,然后检测其后边是否是与def(也可以是其他RE表达式)匹配,若不匹配则该abc符合要求
(?<=...)
positive lookbehind assertion
(?<=abc)def:先在字符串中找到def,然后检测其前边是否与abc相匹配,若匹配则def符合要求
(?<!...)
negative lookbehind assertion
(?<!abc)def:先在字符串中找到def,然后检测其前边是否与abc相匹配,若不匹配则def符合要求
(?(id/name)yes-pattern|no-pattern)
\number
\A
匹配一个字符串的开始。
\b
word boundary.它是一个声明,不占任何宽度,用来标识一个word的开始和结尾。word被定义为一系列数字、字母、下划线组成的序列。
r'\bclass\b'匹配‘this is class A’中的class.不匹配‘the declassified algorithm’中的class
\B
非boundary的时候匹配
如:r'py\B'匹配‘python’,'py3'等,不匹配'py','py'.,'py!'
\d
匹配任意十进制数字,等价于[0-9]
\D
匹配除十进制数字之外的任意数字
\s
匹配任意空白字符。等价于[\t\n\r\f\v]
\S
匹配任意非空白字符。等价于[^\t\n\r\f\v]
\w
匹配任意数字、字母、下划线的字符。等价于[a-zA-Z0-9_]
\W
等价于[^a-zA-Z0-9_]
\Z
匹配字符串的末尾
大多数Python字符串字面值支持的标准逃逸字符同样被正则表达式解释器所接受:如 \a \b \f \n \r \t \v \x \\
注意,\b已经被正则表达式用作word boundaries了,他只有在字符内的时候才表示退格
3.re模块的常用方法和属性
re.compile(pattern,flags=0)
将一个"正则表达式pattern"编译成一个"正则表达式对象",进而可以用正则表达式对象的方法,如match(),search()等。
prog=re.compile(pattern)
result=prog.match(string)
等价于
result=re.match(pattern,string)
但是,当一个正则表达式pattern在一个程序中多次应用的时候,使用re.compile()编译成对象,可以提高效率。
flags可以是以下的一种或多种组合:
re.DEBUG re.I(re.IGNORECASE) re.L(re.LOCALE) re.M(re.MULTILINE) re.S re.DOTALL re.U(re.UNICODE) re.X(re.VERBOSE)
re.search(pattern,string,flags=0)
扫描字符串string,寻找与pattern相匹配的位置,并返回一个MatchObject对象。如果无匹配则返回None。需要支持的是这与在特定场合寻找字符串中的无宽度的匹配不同
re.match(pattern, string, flags=0)
如果字符串string开始的0个或多个字符与pattern相匹配,则返回相应的MatchObjact。否则返回None
re.search() VS re.match():
>>> re.match("c", "abcdef") # No match
>>> re.search("c", "abcdef") # Match
<_sre.SRE_Match object at ...>
>>> re.match("c", "abcdef") # No match
>>> re.search("^c", "abcdef") # No match
>>> re.search("^a", "abcdef") # Match
<_sre.SRE_Match object at ...>
re.split(pattern,string,maxsplit=0,flags=0)
利用pattern来分割字符串。如果pattern用上小括号,则pattern中表示的group也作为返回字符串的一部分。如果maxsplit非零,最多会分割maxsplit次。
>>> re.split('\W+', 'Words, words, words.')
['Words', 'words', 'words', '']
>>> re.split('(\W+)', 'Words, words, words.')
['Words', ', ', 'words', ', ', 'words', '.', '']
>>> re.split('\W+', 'Words, words, words.', 1)
['Words', 'words, words.']
>>> re.split('[a-f]+', '0a3B9', flags=re.IGNORECASE)
['0', '3', '9']
如果开始或结尾就匹配了pattern,则会加上空字符
>>> re.split('(\W+)', '...words, words...')
['', '...', 'words', ', ', 'words', '...', '']
re.findall(pattern, string, flags=0) re.finditer(pattern, string, flags=0) re.sub(pattern, repl, string, count=0, flags=0)
4.正则表达式对象的方法和属性
search(string[, pos[, endpos]]) match(string[, pos[, endpos]]) split(string, maxsplit=0) findall(string[, pos[, endpos]]) finditer(string[, pos[, endpos]]) sub(repl, string, count=0) subn(repl, string, count=0)5. MatchObject对象及其方法
re.MatchObject
Match objects永远有一个bool值True。由于没有匹配成功时match()和search()返回None,所以你可以用一个简单的if语句就可以判断是否生产了一个match,如:
match = re.search(pattern,string)
if match:
process(match)
expand(template)
group([group1,...])
返回match的一个或多个子组(group)。如果只有一个参数,结果就是一个字符串;如果有多个参数,那么结果是一个元组,每个参数对应一项;没有参数的话,group1默认是0(返回整个match字符串)。如果第n个参数groupN是0,那儿它对应的位置就返回整个匹配字符串;如果groupN在1-99之间,则它是match字符串中相应的group对应的字符串。如:
>>> m = re.match(r"(\w+) (\w+)", "Isaac Newton, physicist")
>>> m.group(0) # The entire match
'Isaac Newton'
>>> m.group(1) # The first parenthesized subgroup.
'Isaac'
>>> m.group(2) # The second parenthesized subgroup.
'Newton'
>>> m.group(1, 2) # Multiple arguments give us a tuple.
('Isaac', 'Newton')
lastgroup