正则表达式
1.作用:正则表达式是一种可以让复杂的字符串问题变得简单的工具
2.fulmatch函数
语法:
- fullpmatch(正则表达式, 字符串):判断字符串和正则表达式是否完全匹配(判断整个字符串是否符合正则表达式所描述的规则),如果不符合返回None
python提供正则表达式的方式:
- 直接将正则表示作为一个字符串内容(正则需要使用引号引起来,而且引号前面一般加r)
3.match(正则表达式,字符串):匹配字符串开头
from re import match
print(fullmatch(r'\d','2') != None)#True
print(fullmatch(r'\d','2sdssad') != None)#False
print(match(r'\d','2ZXas') != None)#True
4.findol(正则, 字符串)- 提取字符串中所有满足正则的子串,返回一一个列表
匹配次数:
from re import findall
mess = '<asx12>wqw<123eqwsa>sdad<2wq221e>qw'
re = findall(r'<.+?>',mess)
print(re)#['<asx12>', '<123eqwsa>', '<2wq221e>']
5.split(正则, 字符串):将字符串中所有 满足正则的子串作为切割点对字符串进行切割
from re import split
msg = '2qw*112s*asd,asd你好*撒旦,三大,sada*sad23'
print(split(r'\*',msg))
# ['2qw', '112s', 'asd,asd你好', '撒旦,三大,sada', 'sad23']
6.search(正则,字符串):匹配字符串中第一个满 足正则的字符串
from re import search
msg = '2qw32*112s*asd,asd你好*撒旦,三大,sada*sad23'
print(search(r'\d',msg))# <re.Match object; span=(0, 1), match='2'>
print(search(r'\*\d+',msg))# <re.Match object; span=(5, 9), match='*112'>
7.sub(正则, 字符串1,字符串2):将字符串2中所有满足正则的子串都替换成字符串1
from re import sub
msg = '2qw32*112s*asd,asd你好*撒旦,三大,sada*sad23'
print(sub(r'\d','数字',msg))
#数字qw数字数字*数字数字数字s*asd,asd你好*撒旦,三大,sada*sad数字数字
8.finditer(正则, 字符串):提取字符串中所有满足正则的子串,返回一个迭代器
from re import finditer
msg = '2qw32*112s*asd,asd你好*撒旦,三大,sada*sad23'
print(finditer(r'\d',msg))
# <callable_iterator object at 0x0000023DF44BEEB0>
正则表达式语法:
写正则表达式都是通过正则符号来描述字符串规则
1.匹配类符号:用来规定字符(描述对字符的要求)
普通字符:除了特殊符号以外的符号都是普通字符(再正则中表示符号本身)
from re import fullmatch
print(fullmatch(r'abc','abc') != None)#True:因为需求字符串abc
print(fullmatch(r'abc','abcsdwe') != None)#False字符串'abcsdwe'不满足
特殊符号:
(1).(点):匹配任何一个字符
from re import fullmatch
print(fullmatch(r'a.c','abc') != None)#True:因为需求字符串开头是a结尾是c
print(fullmatch(r'a.c','acc') != None)#True:一个点匹配一个字符
print(fullmatch(r'a..c','acsc') != None)#True
print(fullmatch(r'a...c','acssc') != None)#True
(2)\d:任意匹配一个数字字符
print(fullmatch(r'\d\d\d','123')!= None)#True
print(fullmatch(r'\d{3}','123')!= None)#True
(3)\s:匹配任意一个空白字符:#空白字符:’ ‘、’\n’、‘\t’
print(fullmatch(r'\d\d\s\d','12 3')!= None)#True
print(fullmatch(r'\d\d\s\d','12\n3')!= None)#True
print(fullmatch(r'\d\d\s\d','12\t3')!= None)#True
(4)\w , 匹配任意一个数字、字母、下划线或者中文
print(fullmatch(r'\d\d\w\d','1233')!= None)#True
print(fullmatch(r'\d\d\w\d','12a3')!= None)#True
print(fullmatch(r'\d\d\w\d','12_3')!= None)#True
print(fullmatch(r'\d\d\w\d','12你3')!= None)#True
(5)\D,\W,\S:匹配任意一个非数字(非空格,非数字字母下划线文字)字符zheng
print(fullmatch(r'\d\d\w\d','1233')!= None)#True
print(fullmatch(r'\d\d\W\d','1233')!= None)#False\W不匹配数字字母下划线文字
print(fullmatch(r'\d\d\W\d','12*3')!= None)#True
print(fullmatch(r'\d\d\D\d','12a3')!= None)#True\D不匹配数字
print(fullmatch(r'\d\d\D\d','1233')!= None)#False
print(fullmatch(r'\d\d\d\d','1233')!= None)#True
print(fullmatch(r'\d\d\S\d','12 3')!= None)#False\S不匹配空格字符
print(fullmatch(r'\d\d\S\d','12*3')!= None)#True
print(fullmatch(r'\d\d\s\d','12 3')!= None)#True
(6)
用法一:[字符集]:匹配字符集中的任意一个字符
print(fullmatch(r'a[acd*]c','aac') != None)#匹配[acd*]中的任意一个
print(fullmatch(r'a[acd*]c','acc') != None)#True
print(fullmatch(r'a[acd*]c','adc') != None)#True
print(fullmatch(r'a[acd*]c','a*c') != None)#True
用法二:[字符1-字符2]:匹配字符1到字符2中的任意一个字符
例:[5-9]:匹配5到9中的任意一个字符
例:[a-z]:匹配a到z中的任意一个字符
例:[\u4e00-\u9fa5]:匹配任意一个文字
#[]数字
print(fullmatch(r'[2-3]','2') != None)#True
print(fullmatch(r'[2-3]','3') != None)#True
print(fullmatch(r'[2-3]','4') != None)#False
# 文字
print(fullmatch(r'[\u4e00-\u9fa5]','你') != None)#True
用法三:在[]中包含\开头的特殊符号
[\da-z]:匹配任意一个数字或者任意一个小写字母
[\da-zA-Z_ \u4e00- \u9fa5] = \w
print(fullmatch(r'[\da-z]','a')!= None)#True
print(fullmatch(r'[\da-z][A-Z][\u4e00-\u9fa5]','aA你')!= None)#True
print(fullmatch(r'[\da-z][A-Z][\u4e00-\u9fa5]','3A你')!= None)#True
print(fullmatch(r'[\da-zA-Z\u4e00-\u9fa5]','a')!= None)#True
print(fullmatch(r'[\da-zA-Z\u4e00-\u9fa5]','A')!= None)#True
print(fullmatch(r'[\da-zA-Z\u4e00-\u9fa5]','你')!= None)#True
print(fullmatch(r'[\sa-z][\u4e00-\u9fa5]',' 你')!= None)#True
print(fullmatch(r'[\wa-z][\u4e00-\u9fa5]','你好')!= None)#True
注意:[]中的减号只有在两个字符之间的时候才表示谁到谁
print(fullmatch(r'[az-]az','aaz') != None)#True
print(fullmatch(r'[-az]az','baz') != None)#False
(7)[^字符集]:匹配不在字符集中的任意一个字符
例:[^mn]:除mn以外都可以匹配
print(fullmatch(r'[^mn]','a')!= None)#True
print(fullmatch(r'[^mn]','m')!= None)#False
2.匹配次数
(1)+:匹配1次或者多次(至少1次)
print(fullmatch(r'm+','m')!= None)#True
print(fullmatch(r'm+','mmm')!= None)#True
print(fullmatch(r'm+a','maaa')!= None)#False
print(fullmatch(r'm+a','mmma')!= None)#True,多个m
(2)*:匹配0次或者多个(任意次数)
print(fullmatch(r'm*','mm')!= None)#True
print(fullmatch(r'm*','mmm')!= None)#True
print(fullmatch(r'm*','mmn')!= None)#False不能匹配其他字符
(3)?:匹配0次或者1次
print(fullmatch(r'm?','m')!= None)#True
print(fullmatch(r'm?','')!= None)#True
print(fullmatch(r'm?','mn')!= None)#False
(4){}
{M}:M次
{M,N}:M到N次
{M,}:至少M次
{,N}:最多N次
print(fullmatch(r'm\w{1,4}','mn你好')!= None)#True#m+1-4个数字或字母下划线或者文字
print(fullmatch(r'\\+','\\\\')!= None)#True
(5)贪婪和非贪婪:如果匹配次数不确定,匹配的时候分为贪婪和非贪婪模式两种模式(默认是贪婪模式)
贪婪模式:在多种匹配次数都可以匹配成功的时候,贪婪取最多的次数来进行匹配
非贪婪模式:在多种匹配次数都可以匹配成功的时候,非贪婪取最少的次数来进行匹配(在不确定的匹配次数后面再加一个?)
from re import match
print(match(r'a\w+?a','a21a22a3aaaaZXas'))#True#非贪婪
# <re.Match object; span=(0, 4), match='a21a'>
print(match(r'a\w+a','a2122a3aaaaZXas'))#True#贪婪
# <re.Match object; span=(0, 14), match='a2122a3aaaaZXa'>
3.分组和分支
(1)分组:(),将正则的部分内容括起来表示一个整体
print(fullmatch(r'[\da-z(A-z)]','a'))
print(fullmatch(r'[\da-z(A-z)]','A'))
print(fullmatch(r'[\da-z(A-z)]','2'))
a.整体控制(将正则中一部分内容括起来整体控制次数)
a = '21nm21nm21nm'
print(fullmatch(r'(\d\d[a-z]{2}){3}',a))
#<re.Match object; span=(0, 12), match='21nm21nm21nm'>
b.重复:(在正则中用\M来重复它前面第M个分组匹配到的结果)。
当需要前两个数字与后两个数字相同的字符时如:‘12nm12’,‘23mn23’,匹配成功
a = '21nm21'
print(fullmatch(r'(\d\d)[a-z]{2}\1',a))
#<re.Match object; span=(0, 6), match='21nm21'>
c.捕获:在获取匹配结果的时候可以自动(只有findall有自动捕获的功能)或者手动获取某个分组匹配的结果
自动捕获:如下:
案例1:
from re import findall
mess = '<asx12>wqw<123eqwsa>sdad<2wq221e>qw'
re = findall(r'<(.+?)>',mess)
print(re)
#['asx12', '123eqwsa', '2wq221e']
案例2:捕获数字
from re import findall
mess = '<asx2你1>wqw<22我12我3eqwsa>sdad<222wq22我21我e>qw'
re = findall(r'([\u4e00-\u9fa5]\d+)',mess)
print(re)#['你1', '我12', '我3', '我21']
(2)分支:正则1|正则2|正则3
案例:
# 'abc123'和'abcMKN'二选一
print(fullmatch(r'abc(\d{3}|[A-Z]{3})','abc122'))
print(fullmatch(r'abc(\d{3}|[A-Z]{3})','abcNKK'))
#<re.Match object; span=(0, 6), match='abc122'>
# <re.Match object; span=(0, 6), match='abcNKK'>
4.检测类符号:先匹配,匹配成功后再来看检测类符号所在的位置是否符合相关要求
(1)\b:检测是否是单词边界(单词边界指的是任何可以将两个单词区分开来的符号:空白符号、英文标点符号、字符串开头和字符串结尾)
mess = '<12 asx2 你1>wqw<22 我12,我3 eqwsa>sdad<222wq 22 我21我e>qw12'
print(findall(r'\d+\b',mess))
#['12', '2', '1', '22', '12', '3', '22', '12']
(2)^:检测是否是字符串开头
(3)$:检测是否是字符串结尾
msg = '2qw,112sasd,asd你好撒旦,三大,sadasad23'
print(findall(r'^\d',msg))#['2']
print(findall(r'\d+$',msg))#['23']
5.转义符号:在具有特殊意义的符号前加’\ '让这个有特殊意义的符号变成一个普通符号
案例:匹配任意一个小数
print(fullmatch(r'\d\d\.\d\d','12.12'))
#<re.Match object; span=(0, 5), match='12.12'>
案例:匹配两数相加
print(fullmatch(r'\d\d\+\d\d','12+12'))
# <re.Match object; span=(0, 5), match='12+12'>
补充:除了\开头的特殊符号,其他符号放在[]中对应的特殊功能会自动消失
print(fullmatch(r'\d\d[.]\d\d','12.12'))
#<re.Match object; span=(0, 5), match='12.12'>
print(fullmatch(r'\d\d[+]\d\d','12+12'))
# <re.Match object; span=(0, 5), match='12+12'>