文章目录
- 【README】
- 【7】用正则表达式查找文本
-
- 【7.1】匹配Regex对象
- 【7.2】正则表达式匹配更多模式
- 【7.3】贪心与非贪心匹配
- 【7.4】findAll()方法
- 【7.5】正则表达式缩写字符分类
- 【7.6】插入字符\^与美元字符\$
- 【7.7】通配字符
-
- [【7.7.1】点星字符(.*) 匹配所有字符](#【7.7.1】点星字符(.*) 匹配所有字符)
- [【7.7.2】句点字符(.) 匹配换行符之外的所有字符](#【7.7.2】句点字符(.) 匹配换行符之外的所有字符)
- [【7.7.3】句点字符(.) 匹配所有字符,包括换行符](#【7.7.3】句点字符(.) 匹配所有字符,包括换行符)
- 【7.8】正则表达式符号复习
- 【7.9】不区分大小写匹配
- [【7.10】 用sub()方法替换字符串 (sub=substitute)](#【7.10】 用sub()方法替换字符串 (sub=substitute))
- [【7.11】组合使用 re.IGNORECASE re.DOTALL re.VERBOSE](#【7.11】组合使用 re.IGNORECASE re.DOTALL re.VERBOSE)
【README】
本文总结自《python编程快速上手-让繁琐工作自动化》第7章,非常棒的一本书,墙裂推荐;
【7】用正则表达式查找文本
【7.1】匹配Regex对象
1)创建正则表达式对象
python
phonenumRegExpr = re.compile(r'\d\d\d-\d\d\d-\d\d\d\d')
2)Regex对象的search()方法查找传入的字符串,返回该正则表达式所有的匹配;
- 如果没有找到匹配,返回None;
- 如果找到了匹配,返回Match对象;
- Match 对象的group()方法,返回被查找字符串中实际匹配的文本(分组)
python
import re
phonenumRegExpr = re.compile(r'\d\d\d-\d\d\d-\d\d\d\d')
matchObj = phonenumRegExpr.search('Tom\'s number is 123-456-7890')
print('matched = ' + matchObj.group()) # matched = 123-456-7890
【7.2】正则表达式匹配更多模式
【7.2.1】利用括号分组
python
print('\n\n==== 利用括号分组')
phonenumRegExpr = re.compile(r'(\d\d\d)-(\d\d\d-\d\d\d\d)')
matchObj = phonenumRegExpr.search('Tom\'s number is 123-456-7890')
print(matchObj.group()) # 123-456-7890
print(matchObj.group(0)) # 123-456-7890
print(matchObj.group(1)) # 123
print(matchObj.group(2)) # 456-7890
1)遍历分组
python
# 遍历分组(分组实际上是一个元组)
print('\n\n===遍历分组(分组实际上是一个元组)')
groupTuple = matchObj.groups()
for group in groupTuple:
print(group)
# 123
# 456-7890
2)使用多重赋值读取正则表达式分组
python
print('\n\n===使用多重赋值读取正则表达式分组')
first, second = matchObj.groups()
print(first, second, sep=',') # 123,456-7890
3)正则表达式中的特殊字符需要转译(使用倒斜杠或反斜杠转译 \):包括
python
# 正则表达式中的特殊字符需要转移 包括
# . ^ $ * + ? { } [ ] \ | ( )
# 转译写法: \. \^ \$ \* \+ \? \{ \} \[ \] \\ \| \( \)
【7.2.2】用管道匹配多个分组
1)字符 | 称为管道(或运算),希望匹配多个表达式中的一个时,可以使用它;
python
# 字符|称为管道, 希望匹配许多表达式中的一个时,就可以使用它
print('\n\n===用管道匹配多个分组')
heroRegExpr = re.compile(r'zhangsan|lisi')
print(heroRegExpr.search('zhangsan and lisi').group()) # zhangsan
print(heroRegExpr.search('lisi and zhangsan').group()) # lisi
# 使用管道来匹配多个模式中的一个,这些模式可以是正则表达式中的一部分
print('\n\n===使用管道来匹配多个模式中的一个')
tempRegExpr01 = re.compile(r'Zhangsan(01|02|03)')
print(tempRegExpr01.search('Zhangsan01 is a student').group()) # Zhangsan01
print(tempRegExpr01.search('Zhangsan01 is a student').group(0)) # Zhangsan01
print(tempRegExpr01.search('Zhangsan01 is a student').group(1)) # 01
【7.2.3】用问号实现可选匹配
1) 用?问号匹配0次或1次(如果匹配真正的?号,使用?)
python
print('\n\n===用问号?实现可选匹配 ?匹配0次或1次')
regExpr03 = re.compile(r'zhangsan(110)?')
print(regExpr03.search('zhangsan111').group()) # zhangsan
print(regExpr03.search('zhangsan1100').group()) # zhangsan110
【7.2.4】用*星号匹配0次或多次
1)用*星号匹配0次或多次(如果匹配真正的*号,使用*)
python
print('\n\n===用*星号匹配0次或多次')
regExpr04 = re.compile(r'Abc(wo)*man')
print(regExpr04.search('my name is Abcwoman').group()) # Abcwoman
print(regExpr04.search('my name is Abcman').group()) # Abcman
print(regExpr04.search('my name is Abcwowowoman').group()) # Abcwowowoman
【7.2.5】用+加号匹配一次或多次
1)用+加号匹配一次或多次 (如果匹配真正的+号,使用+)
python
print('\n\n===用+加号匹配一次或多次')
regExpr05 = re.compile(r'Abc(wo)+man')
print(regExpr05.search('my name is Abcwoman').group()) # Abcwoman
print(regExpr05.search('my name is Abcman')) # 匹配失败,返回None, 调用None.group()报错
print(regExpr05.search('my name is Abcwowowoman').group()) # Abcwowowoman
【7.2.6】用花括号匹配特定次数
1)用花括号匹配特定次数 (ha){3} 匹配 'HaHaHa' (ha){3,5} 匹配最少3个ha且最多5个ha的字符串
python
print('\n\n===用花括号匹配特定次数')
regExpr06 = re.compile(r'Abc(wo){3,5}man')
print(regExpr06.search('my name is Abcwoman')) # None 调用None的group()方法会报错
print(regExpr06.search('my name is Abcwowowoman').group()) # Abcwowowoman
print(regExpr06.search('my name is Abcwowowowoman').group()) # Abcwowowowoman
print(regExpr06.search('my name is Abcwowowowowoman').group()) # Abcwowowowowoman
print(regExpr06.search('my name is Abcwowowowowowoman')) # None 调用None的group()方法会报错
【7.3】贪心与非贪心匹配
1)python的正则表达式默认是贪心的,即尽可能匹配最长的字符串;
- 花括号的非贪心是匹配最短的字符串,但需要再结束花括号前跟着一个问号;
python
print('\n\n===贪心与非贪心匹配')
# 贪心 (匹配最长)
greedyHaRegExpr = re.compile(r'(Ha){3,5}')
print(greedyHaRegExpr.search('HaHaHaHaHa').group()) # HaHaHaHaHa
# 非贪心 (匹配最短)
nonGreedyHaRegExpr = re.compile(r'(Ha){3,5}?')
print(nonGreedyHaRegExpr.search('HaHaHaHaHa').group()) # HaHaHa
【7.4】findAll()方法
1)无分组的正则表达式的findall()方法:返回一个字符串列表
python
print('\n\n===正则表达式的findall()方法')
phonenumRegExpr = re.compile(r'\d\d\d-\d\d\d-\d\d\d\d')
print(phonenumRegExpr.findall('home: 123-456-7890 work:111-222-3333'))
# ['123-456-7890', '111-222-3333']
2)有分组的正则表达式的findall()方法:返回匹配的元组列表
python
print('\n\n===有分组的正则表达式的findall()方法:返回元组列表')
phonenumRegExpr = re.compile(r'(\d\d\d)-(\d\d\d)-(\d\d\d\d)')
print(phonenumRegExpr.findall('home: 123-456-7890 work:111-222-3333'))
# [('123', '456', '7890'), ('111', '222', '3333')]
【7.5】正则表达式缩写字符分类
1)用\d表示任何数字, 等价于 (0|1|2|3|4|5|6|7|8|9)
2)用[a-zA-Z]匹配字母;
3)字符分类如下:

【7.6】插入字符^与美元字符$
1)插入字符与美元字符
- 插入字符^ 表示匹配发生在输入字符串的开头
- 美元字符$ 表示匹配发生在输入字符串的结尾
2)同时使用插入字符与美元字符: 表示整个字符串必须匹配该模式,也就是说,只匹配该字符串的某个子集是不够的;
【代码示例】插入字符^ 表示匹配发生在输入字符串的开头
python
print('\n\n===插入字符^ 表示匹配发生在输入字符串的开头')
startWithHello = re.compile('^Hello')
print(startWithHello.search('Hello Wolrd').group()) # Hello
print(startWithHello.findall('Hello Wolrd')) # ['Hello']
print(startWithHello.search('Hello Wolrd') == None) # False
【代码示例】美元字符$ 表示匹配发生在输入字符串的结尾
python
print('\n\n===美元字符$ 表示匹配发生在输入字符串的结尾')
endWithNumber = re.compile(r'\d$')
print(endWithNumber.search('zhangsan001').group()) # 1
【7.7】通配字符
【7.7.1】点星字符(.*) 匹配所有字符
python
print('\n\n===通配字符')
# 点星字符(.*) 匹配所有字符
pointStartRegExpr = re.compile(r'.*')
print(pointStartRegExpr.findall('the cat sat on the flat sofa')) # ['the cat sat on the flat sofa', '']
【7.7.2】句点字符(.) 匹配换行符之外的所有字符
python
# 句点字符(.) 匹配换行符之外的所有字符
pointRegExpr = re.compile(r'.at')
print(pointRegExpr.findall('the cat sat on the flat sofa')) # ['cat', 'sat', 'lat']
【7.7.3】句点字符(.) 匹配所有字符,包括换行符
python
# 传入 re..DOTALL 作为 re.compile()的第2个参数,让句点可以匹配所有字符,包括换行符
newLineRegExpr = re.compile(r'.*', re.DOTALL)
print(newLineRegExpr.search('the cat sat on the flat sofa, \n and i sat on the bed yesterday.'))
print(newLineRegExpr.findall('the cat sat on the flat sofa, \n and i sat on the bed yesterday.'))
# ['the cat sat on the flat sofa, \n and i sat on the bed yesterday.', '']
【7.8】正则表达式符号复习

【7.9】不区分大小写匹配
1)不区分大小写匹配: 把 re.IGNORECASE 或 re.I 作为 re.compile方法的第2个参数
【7.10】 用sub()方法替换字符串 (sub=substitute)
python
substituteExpr = re.compile(r'zhangsan')
print(substituteExpr.sub('lisi', 'zhangsan is a student.'))
# lisi is a student.
【7.11】组合使用 re.IGNORECASE re.DOTALL re.VERBOSE
python
composedExpr = re.compile(r'zhangsan \n and lisi', re.IGNORECASE | re.DOTALL | re.VERBOSE)
print(composedExpr.search('zhangsan \n and LISI are friends')) # None