正则表达式 语法 分组

概念:

使用单个字符串来描述匹配一系列符合某个语法规则的字符
是对字符串操作的一种逻辑公式
一般用来处理文本和数据



re模块

re模块的相关使用方法:

方法 作用
re.match(pattern, string, flags=0) 尝试从字符串起始位置匹配一个模式,如果不是起始位置匹配成功的话,match()就返回None。
re.search(pattern, string, flags=0) 扫描整个字符串并返回第一个成功的匹配。
re.compile(pattern, flags=0) 用于编译正则表达式,生成一个正则表达式(Pattern)对象。
re.findall(pattern, string, flags=0) 在字符串中找到恒则表达式所匹配的所有字串,并返回一个列表 , 如果,没有找到匹配的,则返回空列表。
re.finditer(pattern, string, flags=0) 与findall类似,扫描整个字符串,返回一个迭代器
re.split(pattern, string, maxsplit=0, flags=0) 字符分割操作,re.split:按照能够匹配的子串将字符串分割后返回列表
sub(pattern, repl, string, count=0, flags=0) 在目标字符串中以正则表达式的规则匹配字符串,再把它们替换成指定的字符串。可以指定替换的次数,如果不指定,替换所有的匹配字符串。
subn(pattern, repl, string, count=0, flags=0) 在目标字符串中以正则表达式的规则匹配字符串,再把它们替换成指定的字符串。可以指定替换的次数,如果不指定,替换所有的匹配字符串。

相关方法中的参数说明:

参数 含义
pattern 正则表达式
string 将要匹配的字符串(目标字符串)
flags 标志位,用于控制正则表达式的匹配方式
maxsplit split方法中的参数,分割的最大次数
repl 在sub方法和subn方法中用来替换指定的字符串,也可以是一个函数。
count 在方法sub和方法subn中结合repl参数设置替换的次数

可选标志(flags参数说明):

修饰符 可选标志
re.I 大小写均能匹配
re.L 做本地化识别匹配
re.M 多行匹配,对^和$有影响
re.S 使匹配包括换行在内的所有字符
re.U 根据Unicode字符集解析字符。这个标志影响\w, \W, \b, \B
re.X 该标志通过给予灵活的格式以便将正则表达式写得更容易理解
匹配对象方法 描述
group() 匹配的整个表达式得字符串,group()可以一次输入多个组号,在这种情况下它将返回一个柏寒那些组所对应的元组
groups() 返回一个包含所有小组字符串的元组,从 1 到所含的小组号

正则语法:

字符组的概念:[字符组]

在同一个位置可能出现的各种字符组成了一个字符组,在正则表达式中用 [ ] 表示

字符分为很多种,比如式子,字母,标点等等



元字符 含义
. 匹配任意字符,除了换行符 \n
[…] 匹配字符集
\d \D 分别 匹配数字 , 匹配非数字
\s \S 分别 匹配空白符(空格,换行,回车,换页,制表) ,匹配非空白字符
\w \W 分别 匹配单词字符[a-zA-Z0-9] , 匹配非单词字符
[\W\w] [\S\s] [\D\d] 都可以表示全局
^ 匹配字符串开头 行首匹配
$ 匹配字符串结尾 行尾匹配
\A 匹配整个字符串的开头
\Z 匹配整个字符串的结尾
\n 匹配一个换行符
\t 匹配一个制表符
\b 匹配一个单词的结尾(边界)
a b
() 匹配括号内的表达式,也表示一个组
[…] 匹配字符组中的字符
[^…] 匹配除了字符组中字符的所有字符
* 匹配前一个字符0次或者无限次 贪婪匹配
+ 匹配前一个字符1次或者无限次
? 匹配前一个字符0次或者1次 如果在量词后面,表示惰性匹配的标志。 如果在分组的第一个,就是取消分组优先
{n} 匹配n次
{n,} 匹配n次或者更多次
{n,m} 重复n次或者更多次
*? +? ?? 匹配模式变为非贪婪(惰性匹配(尽可能少匹配字符))
{n,m}? 匹配n到m次,但尽可能少匹配
{n,}? 匹配n次以上,但尽可能少匹配
.? eg: .?x 意思是取前面任意长度的字符,直到x出现,就停止匹配,返回结果

以下的代码是对上面方法参数等的语法演示

1.match方法

import re
# match从头开始找,而且找一个
# match是从头开始匹配,如果正则规则从头开始可以匹配上,就返回一个变量
# 匹配的内容需要用group方法才能显示
# 如果没有匹配上,就返回None,调用group会报错
print("-----------")
ret = re.match('e','eva egon yuan')
print(ret) # 结果:<re.Match object; span=(0, 1), match='e'>
print(ret.group())  # 结果: e

2.search方法

import re
# search找第一个
# search从前往后找到一个就返回   而且返回的是一个变量,必须调用.group()才能拿到结果
# 但如果没有找到,那么返回的是None,调用group会报错
ret = re.search('a','eva egon yuan')
print(ret)	# 结果:<re.Match object; span=(2, 3), match='a'>
print(ret.group())	# 结果: a

3.findall方法:

# findall返回所有满足匹配条件的结果,放在列表里
import re
ret = re.findall('a','eva egon yuan')
print(ret)	# ['a', 'a']

4.finditer方法:

# finditer(pattern, string, flags=0):
# pattern: 正则 
# string: 要匹配的字符
# flags: 标志位,用于控制正则表达式的匹配方式

# 功能:与findall类似,扫描整个字符串,返回一个迭代器
import re

str3 = "shuyv is very handsom! Today shuyv has a girlfriend! And shuyv very happy!"
d = re.finditer(r"(shuyv)",str3)
while True:
    try:
        l = next(d)
        print(d)
    except StopIteration as e:
        break

5.split方法:

# maxsplit的作用是:分割的最大次数。 就以下面例子说明,目标字符中有4个h,
# 当maxsplit大于等于4的时候那么就说明得全部分割得到的结果如下,全部分割。
# 但如果小于4的话,比如3,那么以前三个h分割,后面作为整体一个字符串
import re
ret = re.split('h','abchddddhfaeahwabababhdwabdab',maxsplit=5)
print(ret)   # 得到的是:['abc', 'dddd', 'faea', 'wababab', 'dwabdab']
re.split('h','abchddddhfaeahwabababhdwabdab',maxsplit=3)
print(ret)	 # 得到的是:['abc', 'dddd', 'faea', 'wabababhdwabdab']

6.sub和subn方法:

import re

str2 = "shuyv is a good good good man"

print(re.sub(r"good","nice",str2,count=3))
# 结果: shuyv is a nice nice good man
print(type(re.sub(r"good","nice",str2,count=3)))
# 结果: 'str'>

print(re.subn(r"good","nice",str2))
# 结果: ('shuyv is a nice nice nice man',3)
print(type(re.subn(r"good","nice",str2)))
# 结果: 'tuple'>

# 总结俩者区别:前者返回一个字符出,后者返回一个元组,
# 元组中第一个元素是被替换的字符出,第二个元素是被替换的次数。

7.complie方法:

# 编译:当我们使用正则表达式时,re模块会做俩件事情
# 1、编译正则表达式,如果正则表达式本身不合法,会报错。
# 2、用编译后的正则表达式匹配对象。


pat = r"^1(([3578]\d)|(47))\d{8}$"
print(re.match(pat,"13600000000"))
# '13600000000'>

# 编译正则对象
re_telephone = re.compile(pat)
print(re_telephone.match("13600000000"))
# '13600000000'>


# 总结:complie方法的作用就是将一个正则表达式
# 转换为一个正则对象,通过正则对象直接调用match等方法。
# 注意!!!当你通过complie方法将正则表达式转换为正则对象时,
# 那些方法的参数会发生改变。
# 如上代码所示,match方法后只写了目标字符串(string)

使用complie方法进行编译对象后方法参数的变化如下表所示。结合7中的代码,重点关注方法中参数的增减

re模块调用 re对象调用
re.match(pattern,string,flags=0) re_telephone.match(string)
re.search(pattern,string,flags=0) re_telephone.search(string)
re.findall(pattern,string,flags=0) re_telephone.findall(string)
re.finditer(pattern,string,flags=0) re_telephone.findier(string)
re.split(pattern, string, maxsplit=0, flags=0) re_telephone.split(string,maxsplit=0)
re.sub(pattern, repl, string, count=0, flags=0) re_telephone.sub(repl,string,count=0)
re.subn(pattern, repl, string, count=0, flags=0) re_telephone.subn(repl,string,count=0)


分组(重点理解)

分组:在正则中用小括号()表示

作用:将某些规律看成是一组,然后进行则级别的调用。通过分组可以读取 “子字符”(我这里的子字符代表每个组中的正则表达式所匹配的结果字符串)的信息。

代码演示:

# 此处以身份证号来举例

import re

pattern = '^[1-9](\d{14})(\d{2}[1-9x])?$'
str3 = '162626200011110112'

ret = re.search(pattern,str3)

print(ret.group(0))	# 162626200011110112
print(ret.group(1))	# 62626200011110
print(ret.group(2))	# 112

# 可以使用groups方法来查看各组的情况
print(ret.groups())	
# 结果:('62626200011110', '112')
# 返回结果是一个元组,并且不包括 原始组(就是整个字符串)

由以上代码可知:
对于分组而言,整个表达式永远作为第0组(原始组)

除了使用序号来读取各组信息,还可以通过给各组起名字来读取各组信息。代码如下:

str6 = "010-53247654"
m = re.match(r"(\d{3})-(\d{8})",str6)

# 使用序号获取各组信息,group(0)代表的是原始字符串(整个字符串)
print(m.group(0))   # 010-53247654
print(m.group(1))   # 010
print(m.group(2))   # 53247654

# 除了通过序号来查看组的信息,还可以给组起名,通过名字来获取信息 ?P
m = re.match(r"(?P\d{3})-(?P\d{8})",str6)
print(m.group("first")) # 010
print(m.group("last"))  # 53247654

# 如上代码,我们用?P这种语法格式来给各组起名字,然后通过名字来读取各组信息。

!!!!!!!!!!!!!!!!!!!!!!!!



补充说明:正则表达式和re模块的关系:

1,正则表达式本身和python没什么关系,就是匹配字符串的一种规则。
2,而在python中,通过内嵌集成re模块,程序媛们可以直接调用来实现正则匹配,正则表达式被编译成一系列的字节码,然后用由C编写的匹配引擎执行。



你可能感兴趣的:(正则表达式,python3)