首页 > 技术文章 > re 模块

quqinchao 2019-07-28 08:33 原文

1. re模块方法

1.1 match()

  • 定义:从字符串起始位置匹配,如果不是起始位置匹配成功就返回None
print(re.match('e','elex make love'))
结果:<_sre.SRE_Match object; span=(0, 1), match='e'>
通过group()得到匹配的字符串
  • 定义: 扫描整个字符串并返回第一个成功的匹配
    可以通过调用group()方法得到匹配的字符串,如果字符串没有匹配,则返回None
print(re.search('e','alex make love'))
结果:<_sre.SRE_Match object; span=(2, 3), match='e'>
print(re.search('e','alex make love').group())

1.3 findall

  • 定义:在字符串中找到正则表达式所匹配的所有子符串,并返回一个列表,如果没有找到匹配的,则返回空列表。
print(re.findall('e','alex make love'))   #['e', 'e', 'e']

1.4 split()

  • 定义:按照能够匹配的子串将字符串分割后返回列表
print(re.split('[ab]','abcd'))
先按'a'分割得到''和'bcd',再对''和'bcd'分别按'b'分割
#['', '', 'cd']

1.5 sub()

  • 定义:替换字符串的匹配项
  • 语法:re.sub(pattern, repl, string, count=0, flags=0)
print(re.sub('a','A','alex make love'))
# Alex mAke love (不指定n,默认替换所有)

字符串后可以指定替换的次数
re.sub('a','A','alex make love',1)

print(re.sub('[a-z]+xx','yxp','lxx is good,sb is lllxx wxx is good cxx is good'))
#yxp is good,sb is yxp yxp is good yxp is good
  • 例题
phone = "2004-959-559 # 这是一个国外电话号码"
 
# 删除字符串中的 Python注释 
num = re.sub(r'#.*$', "", phone)
print "电话号码是: ", num
 
# 删除非数字(-)的字符串 
num = re.sub(r'\D', "", phone)
print "电话号码是 : ", num

1.6 compile 函数

  • 编译正则表达式,生成一个正则表达式对象
  • pattern = re.compile(表达式)
pattern=re.compile('alex')
调用得到的对象pattern去匹配
print(pattern.findall('alex is SB,alex is bigSB'))
print(pattern.search('alex is SB,alex is bigSB'))

1.7 re.S 与re.M

import  re
# string1 = """<div>静夜思
# 窗前明月光
# 疑是地上霜
# 举头望明月
# 低头思故乡
# </div>"""
print(re.findall('.*',string1,re.S))
结果:['<div>静夜思\n窗前明月光\n疑是地上霜\n举头望明月\n低头思故乡\n</div>', '']
#如果不使用re.S参数,则只在每一行内进行匹配,如果一行没有,就换下一行重新开始,不会跨行。
# 而使用re.S参数以后,正则表达式会将这个字符串作为一个整体,将“\n”当做一个普通的字符加入到这个字符串中,在整体中进行匹配

#匹配以i 开头的行
# string = '''fall in love with you
# i love you very much
# i love she
# i love her'''
print(re.findall('^i.*',string,re.M))
#re.M表示将字符串视为多行,从而^匹配每一行的行首,$匹配每一行的行尾

2. 特殊字符匹配

 print(re.findall('\w','holle peter 123')) 匹配数字字母下划线
 print(re.findall('\W','holle peter 123'))#匹配非字母数字下划线
 print(re.findall('\s',"holle peter 123"))#匹配任意的空白字符
 print(re.findall('\S','holle prter 123'))# 匹配任意非空字符
 print(re.findall('\d','holle prter 123')) 匹配任意数字
 print(re.findall('\D','holle prter 123')) 匹配任意非数字
 print(re.findall('\n','holle prter 123'))匹配换行符,没有返回空列表
 print(re.findall('\t','holle prter 123'))匹配制表符
 print(re.findall('^h','hello egon 123'))  匹配字符串是否以h开始,是返回h,不是返回空列表
 print(re.findall('3$','hello egon 123')) 匹配换行结束前的字符串是否以3结束,是返回3,不是返回空列表

3. 重复匹配 . [] * ? + {n,m}

3.1 . 匹配任意一个字符,除了换行符,被re.DOTALL指定的可以匹配任意字符

print(re.findall('a.b','a1b')) #['a1b']
print(re.findall('a.b','a1b a*b a b aaab')) #['a1b', 'a*b', 'a b', 'aab']
print(re.findall('a.b','a\nb')) #[]
print(re.findall('a.b','a\nb',re.S)) #['a\nb']
print(re.findall('a.b','a\nb',re.DOTALL)) #['a\nb']同上一条意思一样
(a.b 平移对照,a和b的位置都要对上)

3.2 [] 匹配一个字符,该字符属于中括号内指定字符

print(re.findall('a[a-z]c','abc a1 c aac aAc aBc asd aaaaac a-c a/c a *c a+c abasd = a1c a2c'))
结果:['abc', 'aac', 'aac']
print(re.findall('a[^a-z]c','abc a1 c aac aAc aBc asd aaaaac a-c a/c a *c a+c abasd = a1c a2c'))
结果:['aAc', 'aBc', 'a-c', 'a/c', 'a+c', 'a1c', 'a2c']
 注:^加入中括号表示取反,除了小写字母以外全都可以

3.3 *必须与其他字符连用,代表左侧的字符出现0次或者无穷次

print(re.findall('ab*','a ab abbb abbbb a1bbbb a-123'))
结果:['a', 'ab', 'abbb', 'abbbb', 'a', 'a']
注:*号的左侧即b位置无论有没有都取走

3.4 ? 必须与其他字符连用,代表左侧的字符出现0次或者1次

print(re.findall('ab?','a ab abbb abbbb a1bbbb a-123'))
结果:['a','ab','ab','ab','a','a']

3.5 +必须与其他字符连用,代表左侧的字符出现1次或者无穷次

print(re.findall('ab+','a ab abbb abbbb a1bbbb a-123'))
结果:['ab','abbb','abbbb']

3.6 {n,m} 指定左侧字符出现次数的范围

print(re.findall('ab{1,3}','a ab abbb abbbb a1bbbb a-123'))
结果:['ab','abbb','abbb']
注:取左侧字符出现1次至3次的值

3.7 ()分组

print(re.findall('expression="(.*?)"','expression="1+2+3/4*5" egon="beautiful"'))
结果:['1+2+3/4*5']
在第一次匹配后再取出括号内的值

3.8 .* 贪婪匹配

print(re.findall('a.*b','a1b22222222b')) #['a1b22222222b']

3.9 .*? 非贪婪匹配

print(re.findall('a.*?b','a1b22222222b')) #['a1b']
print(re.findall(r":(.*?@.*?com)",'email1:378533872@qq.com email2:333312312@163.com email3:alexsb123@gmail.com'))
# ['378533872@qq.com', '333312312@163.com', 'alexsb123@gmail.com']

3.10 | 或 两边条件有一个满足就被取出

print(re.findall('a|b', 'ab123abasdfaf'))
#['a', 'b', 'a', 'b', 'a', 'a']

#取出compan开头的字符
b='Too many companies have gone bankrupt, and the next one is my company'
print(re.findall('compan(?:ies|y)',b))
#['companies', 'company']
注:组内条件是只要满足 ies或者y 就取出,前面加一个?:表示取整体,不仅仅取组内

补充:正则识别字符过程及转义特殊字符含义

两种方法:
print(re.findall(r'a\\c','a\c a1c aAc aac'))
#首先是pychrm 识别,r后面跟的是原生字符串,提交给re模块识别第一个斜杠是转义,第二个变成了普通斜杠
print(re.findall(r'a\\\\c','a\c a1c aAc aac'))
#pychrm先识别得到a\\c, re模块再识别得到a\b,输出结果为a\\b

推荐阅读