博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
4Python全站之路系列之正则表达式re模块
阅读量:5789 次
发布时间:2019-06-18

本文共 7257 字,大约阅读时间需要 24 分钟。

正则表达式并不是Python的一部分。正则表达式是用于处理字符串的强大工具,拥有自己独特的语法以及一个独立的处理引擎,效率上可能不如str自带的方法,但功能十分强大。得益于这一点,在提供了正则表达式的语言里,正则表达式的语法都是一样的,区别只在于不同的编程语言实现支持的语法数量不同;但不用担心,不被支持的语法通常是不常用的部分。如果已经在其他语言里使用过正则表达式,只需要简单看一看就可以上手了。


正则表达式概念

  1. 使用单个字符串来描述匹配一系列符合某个句法规则的字符串

  2. 是对字符串操作的一种逻辑公式

  3. 应用场景:处理文本和数据

  4. 正则表示是过程:依次拿出表达式和文本中的字符比较,如果每一个字符都能匹配,则匹配成功;否则匹配失败

字符匹配

字符 描述
. 匹配任意一个字符(除了\n)
\d \D 数字/非数字
\s \S 空白/非空白字符
\w \W 单词字符[a-zA-Z0-9]/非单词字符
\b \B 单词边界,一个\w与\W之间的范围,顺序可逆/非单词边界
  • 匹配任意一个字符

1
2
3
4
 
# 匹配字符串abc,.代表b
 
>>>import re
 
>>> re.match(
'a.c'
,
'abc'
).group()
'abc'
  • 数字与非数字

1
2
3
4
5
6
 
# 匹配任意一数字
 
>>> re.match(
'\d'
,
'1'
).group()
'1'
 
# 匹配任意一个非数字
 
>>> re.match(
'\D'
,
'a'
).group()
'a'
  • 空白与非空白字符

1
2
3
4
5
6
7
8
 
# 匹配任意一个空白字符
 
>>> re.match(
"\s"
,
" "
).group()
' '
 
# 匹配任意一个非空白字符
 
>>> re.match(
"\S"
,
"1"
).group()
'1'
 
>>> re.match(
"\S"
,
"a"
).group()
'a'
  • 单词字符与非单词字符

单词字符即代表[a-zA-Z0-9]

1
2
3
4
5
6
7
8
 
# 匹配任意一个单词字符
 
>>> re.match(
"\w"
,
"a"
).group()
'a'
 
>>> re.match(
"\w"
,
"1"
).group()
'1'
 
# 匹配任意一个非单词字符
 
>>> re.match(
"\W"
,
" "
).group()
' '

次数匹配

字符 匹配
* 匹配前一个字符0次或者无限次
+ 匹配前一个字符1次或者无限次
? 匹配前一个字符0次或者1次
{m}/{m,n} 匹配前一个字符m次或者N次
*?/+?/?? 匹配模式变为贪婪模式(尽可能少匹配字符)
  • 介绍

字符 匹配
prev? 0个或1个prev
prev* 0个或多个prev,尽可能多地匹配
prev*? 0个或多个prev,尽可能少地匹配
prev+ 1个或多个prev,尽可能多地匹配
prev+? 1个或多个prev,尽可能少地匹配
prev{m} m个连续的prev
prev{m,n} m到n个连续的prev,尽可能多地匹配
prev{m,n}? m到n个连续的prev,尽可能少地匹配
[abc] a或b或c
[^abc] 非(a或b或c)
  • 匹配前一个字符0次或者无限次

1
2
3
4
5
6
 
>>> re.match(
'[A-Z][a-z]*'
,
'Aaa'
).group()
'Aaa'
 
>>> re.match(
'[A-Z][a-z]*'
,
'Aa'
).group()
'Aa'
 
>>> re.match(
'[A-Z][a-z]*'
,
'A'
).group()
'A'
  • 匹配前一个字符1次或者无限次

1
2
3
4
5
 
# 匹配前一个字符至少一次,如果一次都没有就会报错
 
>>> re.match(
'[A-Z][a-z]+'
,
'A'
).group()
Traceback (most recent call last):
  
File 
"<stdin>"
, line 
1
in 
<module>
AttributeError: 
'NoneType' 
object 
has no attribute 
'group'
1
2
3
4
 
>>> re.match(
'[A-Z][a-z]+'
,
'Aa'
).group()
'Aa'
 
>>> re.match(
'[A-Z][a-z]+'
,
'Aaaaaaa'
).group()
'Aaaaaaa'
  • 匹配前一个字符0次或者1次

1
2
3
4
5
 
>>> re.match(
'[A-Z][a-z]?'
,
'A'
).group()
'A'
 
# 只匹配出一个a
 
>>> re.match(
'[A-Z][a-z]?'
,
'Aaaa'
).group()
'Aa'
  • 匹配前一个字符m次或者N次

1
2
3
4
5
6
7
8
9
 
#匹配前一个字符至少5次
 
>>> re.match(
'\w{5}'
,
'asd234'
).group()
'asd23'
 
# 匹配前面的字符6-10次
 
>>> re.match(
'\w{6,10}'
,
'asd234'
).group()
'asd234'
 
# 超过的字符就匹配不出来
 
>>> re.match(
'\w{6,10}'
,
'asd2313qeadsd4'
).group()
'asd2313qea'
  • 匹配模式变为贪婪模式

1
2
3
4
5
6
7
8
9
10
11
 
>>> re.match(r
'[0-9][a-z]*'
,
'1bc'
).group()
'1bc'
 
# *?匹配0次或者多次
 
>>> re.match(r
'[0-9][a-z]*?'
,
'1bc'
).group()
'1'
 
# +?匹配一次或者多次,但是只匹配了一次
 
>>> re.match(r
'[0-9][a-z]+?'
,
'1bc'
).group()
'1b'
 
# ??匹配0次或者一次
 
>>> re.match(r
'[0-9][a-z]??'
,
'1bc'
).group()
'1'

贪婪匹配和非贪婪匹配

边界匹配

字符 匹配
^ 匹配字符串开头
$ 匹配字符串结尾
\A \Z 指定的字符串必须出现在开头/结尾
  • 匹配字符串开头

1
2
3
# 必须以指定的字符串开头,结尾必须是@163.com
 
>>> re.match(
'^[\w]{4,6}@163.com$'
,
'asdasd@163.com'
).group()
'asdasd@163.com'
  • 匹配字符串结尾

1
2
3
 
# 必须以.me结尾
 
>>> re.match(
'[\w]{1,20}.me$'
,
'ansheng.me'
).group()
'ansheng.me'
  • 指定的字符串必须出现在开头/结尾

1
2
 
>>> re.match(r
'\Awww[\w]*\me'
,
'wwwanshengme'
).group()
'wwwanshengme'

正则表达式分组匹配

  • | 匹配左右任意一个表达式

1
2
3
4
 
>>> re.match(
"www|me"
,
"www"
).group()
'www'
 
>>> re.match(
"www|me"
,
"me"
).group()
'me'
  • (ab) 括号中表达式作为一个分组

1
2
3
4
5
# 匹配163或者126的邮箱
 
>>> re.match(r
'[\w]{4,6}@(163|126).com'
,
'asdasd@163.com'
).group()
'asdasd@163.com'
 
>>> re.match(r
'[\w]{4,6}@(163|126).com'
,
'asdasd@126.com'
).group()
'asdasd@126.com'
  • (?P) 分组起一个别名

1
2
 
>>> re.search(
"(?P<zimu>abc)(?P<shuzi>123)"
,
"abc123"
).groups()
(
'abc'
'123'
)
  • 引用别名为name的分组匹配字符串

1
2
3
4
 
>>> res.group(
"shuzi"
)
'123'
 
>>> res.group(
"zimu"
)
'abc

re模块常用的方法

  • re.match()

语法格式:

1
match(pattern, string, flags
=
0
)

释意:

Try to apply the pattern at the start of the string, returning a match object, or None if no match was found.

实例:

1
2
3
4
5
6
7
8
 
# 从头开始匹配,匹配成功则返回匹配的对象
 
>>> re.match(
"abc"
,
"abc123def"
).group()
'abc'
 
# 从头开始匹配,如果没有匹配到对应的字符串就报错
 
>>> re.match(
"\d"
,
"abc123def"
).group()
Traceback (most recent call last):
  
File 
"<stdin>"
, line 
1
in 
<module>
AttributeError: 
'NoneType' 
object 
has no attribute 
'group'
  • re.search()

语法格式:

1
search(pattern, string, flags
=
0
)

释意:

Scan through string looking for a match to the pattern, returning a match object, or None if no match was found.

实例:

1
2
3
 
# 匹配整个字符串,匹配到第一个的时候就返回匹配到的对象
 
>>> re.search(
"\d"
,
"abc1123def"
).group()
'1'
  • re.findall()

语法格式:

1
findall(pattern, string, flags
=
0
)

释意:

Return a list of all non-overlapping matches in the string.

实例:

1
2
3
 
# 匹配字符串所有的内容,把匹配到的字符串以列表的形式返回
 
>>> re.findall(
"\d"
,
"abc123def456"
)
[
'1'
'2'
'3'
'4'
'5'
'6'
]
  • re.split

语法格式:

1
split(pattern, string, maxsplit
=
0
)

释意:

Split the source string by the occurrences of the pattern, returning a list containing the resulting substrings.

实例:

1
2
3
4
5
6
 
# 指定以数字进行分割,返回的是一个列表对象
 
>>> re.split(
"\d+"
,
"abc123def4+-*/56"
)
[
'abc'
'def'
'+-*/'
, '']
 
# 以多个字符进行分割
 
>>> re.split(
"[\d,]"
,
"a,b1c"
)
[
'a'
'b'
'c'
]
  • re.sub()

语法格式:

1
sub(pattern, repl, string, count
=
0
)

释意:

Return the string obtained by replacing the leftmost non-overlapping occurrences of the pattern in string by the replacement repl. repl can be either a string or a callable;

if a string, backslash escapes in it are processed. If it is a callable, it’s passed the match object and must return a replacement string to be used.

实例:

1
2
3
4
5
6
 
# 把abc替换成def
 
>>> re.sub(
"abc"
,
"def"
,
"abc123abc"
)
'def123def'
 
# 只替换查找到的第一个字符串
 
>>> re.sub(
"abc"
,
"def"
,
"abc123abc"
,count
=
1
)
'def123abc'

实例

string方法包含了一百个可打印的ASCII字符,大小写字母、数字、空格以及标点符号

1
2
3
4
 
>>> 
import 
string
 
>>> printable 
= 
string.printable
 
>>> printable
'0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ!"#$%&\'()*+,-./:;<=>?@[\\]^_`{|}~ \t\n\r\x0b\x0c'
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
>>> 
import 
re
 
# 定义的字符串
 
>>> source 
= 
'''I wish I may, I wish I migth
... Hava a dish of fish tonight.'''
 
 
# 在字符串中检索wish
 
>>> re.findall(
'wish'
,source)
[
'wish'
'wish'
]
 
 
# 对源字符串任意位置查询wish或者fish
 
>>> re.findall(
'wish|fish'
,source)
[
'wish'
'wish'
'fish'
]
  
 
# 从字符串开头开始匹配wish
 
>>> re.findall(
'^wish'
,source)    
[]
  
 
# 从字符串开头匹配I wish
 
>>> re.findall(
'^I wish'
,source)
[
'I wish'
]
  
 
# 从字符串结尾匹配fish
 
>>> re.findall(
'fish$'
,source)   
[]
 
# 从字符串结尾匹配fish tonight.
 
>>> re.findall(
'fish tonight.$'
,source)
[
'fish tonight.'
]
  
 
# 查询以w或f开头,后面紧跟着ish的匹配
 
>>> re.findall(
'[wf]ish'
,source)
[
'wish'
'wish'
'fish'
]
 
 
# 查询以若干个w\s\h组合的匹配
 
>>> re.findall(
'[wsh]+'
,source) 
[
'w'
'sh'
'w'
'sh'
'h'
'sh'
'sh'
'h'
]
 
 
# 查询以ght开头,后面紧跟着一个非数字和字母的匹配
 
>>> re.findall(
'ght\W'
,source)
[
'ght.'
]
 
 
# 查询已以I开头,后面紧跟着wish的匹配
 
>>> re.findall(
'I (?=wish)'
,source)
[
'I '
'I '
]
 
 
# 最后查询以wish结尾,前面为I的匹配(I出现次数尽量少)
 
>>> re.findall(
'(?<=I) wish'
,source)
[
' wish'
' wish'
]
  • 匹配时不区分大小写

1
2
 
>>> re.match(
'a'
,
'Abc'
,re.I).group()
'A'
  • r 源字符串,转义,如果要转义要加两个\n

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
 
>>> 
import 
re
 
>>> pa 
= 
re.
compile
(r
'ansheng'
)
 
>>> pa.match(
"ansheng.me"
)
<_sre.SRE_Match 
object
; span
=
(
0
7
), match
=
'ansheng'
>
 
>>> ma 
= 
pa.match(
"ansheng.me"
)
 
>>> ma
<_sre.SRE_Match 
object
; span
=
(
0
7
), match
=
'ansheng'
>
 
# 匹配到的值存到group内
 
>>> ma.group()
'ansheng'
 
# 返回字符串的所有位置
 
>>> ma.span()
(
0
7
)
 
# 匹配的字符串会被放到string中
 
>>> ma.string
'ansheng.me'
 
# 实例放在re中
 
>>> ma.re
re.
compile
(
'ansheng'
)
本文转自 Edenwy  51CTO博客,原文链接:http://blog.51cto.com/edeny/1915504,如需转载请自行联系原作者
你可能感兴趣的文章
视频图像处理基础知识0(双线性插值算法进行图像缩放)【转】
查看>>
c语言中基本数据类型printf()对应格式
查看>>
如何保证缓存与数据库的双写一致性?
查看>>
Jar运行的几个方法
查看>>
验证二叉搜索树的golang实现
查看>>
读书笔记《自控力》
查看>>
浅议.NET、ASP.NET和C#的关系
查看>>
12.04 安装svn
查看>>
2017 3月15日 上午
查看>>
基于神念TGAM的脑波小车(1)
查看>>
ceph集群搭建Jewel版本
查看>>
HttpClient 解释
查看>>
111111
查看>>
在Button上面显示图片,去掉Button的默认样式
查看>>
区域生长算法
查看>>
(转)json+flexgrid+jbox组合运用页面刷新<jsp>
查看>>
hive学习2(Navicat连接hive)
查看>>
getResourceAsStream的3种路径配置
查看>>
switch语句小练习
查看>>
组合逻辑电路
查看>>