re 模块概述
re,也就是正则表达式,用来从字符串中获取我们想要的内容:
1 | import re |
输出的结果为:
1 | ['e', 'e', 'e', 'e'] |
元字符
正则表达式的当然不仅仅能查找这种简单地字符。正则表达式真正的强大之处在于它无所不包的匹配规则。这一套匹配规则对于所有语言来说都是通用的,通过一个个元字符组合而成:
元字符 | 匹配内容 |
---|---|
\w | 匹配字母(包括中文)、数字或下划线 |
\W | 匹配除字母(包括中文)、数字或下划线以外的字符 |
\s | 匹配任意空白字符 |
\S | 匹配任意非空白字符 |
\d | 匹配任意数字 |
\D | 匹配任意非数字字符 |
\A或^ | 从字符串的开头匹配。若指定 re.MULTILINE 或 re.M,则从字符串开头或换行符后匹配 |
\Z或$ | 从字符串的结尾匹配。若指定 re.MULTILINE 或 re.M,则从字符串结尾或换行符前匹配 |
. | 匹配任意字符,除了换行符。当 re.DOTALL 或 re.S 标记被指定时,则可以匹配包括换行符的任意字符 |
[0-9a-zA-Z] | 用于匹配特定范围的数字和字母,中间不能有空格和逗号 |
* | 匹配 0 个或多个左边的字符,贪婪匹配(匹配尽可能长的内容) |
+ | 匹配 1 个或多个左边的字符,贪婪匹配 |
? | 匹配 0 个或 1 个左边的字符,非贪婪匹配。也可以用来将 * 和 + 转换为非贪婪匹配模式 |
{n} | 精准匹配 n 个前面的字符 |
{n, m} | 匹配 n 到 m 个前面的字符片段,贪婪匹配 |
a|b | a 或者 b,优先匹配 a |
() | 匹配括号内的表达式,也表示一个组 |
注:若 re.MULTILINE
和 re.DOTALL
需要同时指定,可以使用并集,即 flags=re.DOTALL | re.MULTILINE
正则表达式的使用方法为:
1 | s = 'alex1, 哈啰,123,meet!@' |
正则匹配练习
接下来,我们就通过一些练习题,更加深入理解正则表达式的用法。
有如下字符串:
'alex_sb ale123_sb wu12sir_sb wusir_sb ritian_sb 的 alex wusir '
,找到其中所有带_sb
的内容。要求,输出结果中也要包含_sb
。1
2
3
4
5import re
s = 'alex_sb ale123_sb wu12sir_sb wusir_sb ritian_sb 的 alex wusir '
print(re.findall('\w[(?:.+?)]_sb', s)) # 第二个?用来让+变成非贪婪匹配
print(re.findall('\w[a-z0-9]+_sb', s))
print(re.findall('(\w.+?_sb) ', s))输出结果全都为:
1
['alex_sb', 'ale123_sb', 'wu12sir_sb', 'wusir_sb', 'ritian_sb']
有字符串
"1-2*(60+(-40.35/5)-(-4*3))"
,- 请找出字符串中的所有整数
- 请找出字符串中的所有数字(包含小数)
- 请找出所有的数字(正数、负数和小数)
1
2
3
4
5import re
s = "1-2*(60+(-40.35/5)-(-4*3))"
print(re.findall('\d+', s))
print(re.findall('\d+\.?\d*', s))
print(re.findall('-?\d+\.?\d*', s))输出的结果为:
1
2
3['1', '2', '60', '40', '35', '5', '4', '3']
['1', '2', '60', '40.35', '5', '4', '3']
['1', '-2', '60', '-40.35', '5', '-4', '3']请找出字符串
"http://blog.csdn.net/make164492212@163.com/article/details/51656638"
中的邮箱。1
2
3import re
s = "http://blog.csdn.net/make164492212@163.com/article/details/51656638"
print(re.findall('\w+@\w+\.\w+', s))输出的结果为:
1
['make164492212@163.com']
请找出下列字符串中的
- 所有形如
1995-04-27
的时间 - 形如
1980-04-27:1980-04-27
的时间
1
2
3
4
5
6
7
8
9import re
s = '''
时间就是1995-04-27,2005-04-27
1999-04-27 老男孩教育创始人
老男孩老师 alex 1980-04-27:1980-04-27
2018-12-08
'''
print(re.findall('\d{4}-\d{2}-\d{2}', s))
print(re.findall('(\S+:\S+)'))输出的结果为:
1
2['1995-04-27', '2005-04-27', '1999-04-27', '1980-04-27', '1980-04-27', '2018-12-08']
['1980-04-27:1980-04-27']- 所有形如
匹配字符串
"1231,11,2,1,-1,12.34545,abc,ssed"
中的浮点数1
2
3import re
s = "1231,11,2,1,-1,12.34545,abc,ssed"
print(re.findall('\d+\.\d+', s))输出的结果为:
1
['12.34545']
匹配字符串
"1231231,324233,123,1123,2435,1234,2546,23451324,3546354,13241234"
中可能的 QQ 号(5 - 11 位)。1
2
3import re
s = "1231231,324233,123,1123,2435,1234,2546,23451324,3546354,13241234"
print(re.findall('\d{5,11}', s))输出的结果为:
1
['1231231', '324233', '23451324', '3546354', '13241234']
有下面一个长数据,请找出其中a标签中href后的网址(如
http://www.cnblogs.com/guobaoyuan/articles/7087629.html
)。1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22import re
msg = '''
<div id="cnblogs_post_body" class="blogpost-body"><h3><span style="font-family: 楷体;">python基础篇</span></h3>
<p><span style="font-family: 楷体;"> <strong><a href="http://www.cnblogs.com/guobaoyuan/p/6847032.html" target="_blank">python 基础知识</a></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/p/6627631.html" target="_blank">python 初始python</a></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <strong><a href="http://www.cnblogs.com/guobaoyuan/articles/7087609.html" target="_blank">python 字符编码</a></strong></strong></span></p>
<p><span style="font-family: 楷体;"><strong><strong> <a href="http://www.cnblogs.com/guobaoyuan/articles/6752157.html" target="_blank">python 类型及变量</a></strong></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/p/6847663.html" target="_blank">python 字符串详解</a></strong></span></p>
<p><span style="font-family: 楷体;"> <strong><a href="http://www.cnblogs.com/guobaoyuan/p/6850347.html" target="_blank">python 列表详解</a></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/p/6850496.html" target="_blank">python 数字元祖</a></strong></span></p>
<p><span style="font-family: 楷体;"> <strong><a href="http://www.cnblogs.com/guobaoyuan/p/6851820.html" target="_blank">python 字典详解</a></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <strong> <a href="http://www.cnblogs.com/guobaoyuan/p/6852131.html" target="_blank">python 集合详解</a></strong></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/articles/7087614.html" target="_blank">python 数据类型</a> </strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/p/6752169.html" target="_blank">python文件操作</a></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/p/8149209.html" target="_blank">python 闭包</a></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/articles/6705714.html" target="_blank">python 函数详解</a></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/articles/7087616.html" target="_blank">python 函数、装饰器、内置函数</a></strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/articles/7087629.html" target="_blank">python 迭代器 生成器</a> </strong></span></p>
<p><span style="font-family: 楷体;"><strong> <a href="http://www.cnblogs.com/guobaoyuan/articles/6757215.html" target="_blank">python匿名函数、内置函数</a></strong></span></p>
</div>
'''
print(re.findall('href="(.+?)"'))输出的结果为:
1
['http://www.cnblogs.com/guobaoyuan/p/6847032.html', 'http://www.cnblogs.com/guobaoyuan/p/6627631.html', 'http://www.cnblogs.com/guobaoyuan/articles/7087609.html', 'http://www.cnblogs.com/guobaoyuan/articles/6752157.html', 'http://www.cnblogs.com/guobaoyuan/p/6847663.html', 'http://www.cnblogs.com/guobaoyuan/p/6850347.html', 'http://www.cnblogs.com/guobaoyuan/p/6850496.html', 'http://www.cnblogs.com/guobaoyuan/p/6851820.html', 'http://www.cnblogs.com/guobaoyuan/p/6852131.html', 'http://www.cnblogs.com/guobaoyuan/articles/7087614.html', 'http://www.cnblogs.com/guobaoyuan/p/6752169.html', 'http://www.cnblogs.com/guobaoyuan/p/8149209.html', 'http://www.cnblogs.com/guobaoyuan/articles/6705714.html', 'http://www.cnblogs.com/guobaoyuan/articles/7087616.html', 'http://www.cnblogs.com/guobaoyuan/articles/7087629.html', 'http://www.cnblogs.com/guobaoyuan/articles/6757215.html']
正则表达式常用方法
除了 findall 外,正则表达式的常用方法还有 search,match 等:
1 | import re |
输出的结果为:
1 | ['e', 'e', 'e'] |
search 方法和 match 方法的比较:
- search 方法从字符串任意位置进行匹配,查找到一个就停止
- match 方法从字符串开始位置进行匹配,找不到返回 None
除了上面的几个方法,re 中还有一些不常用但也很有用的方法:
1 | import re |
面试题:
- 什么是贪婪匹配和非贪婪匹配?
- search 和 match 的区别?