python re正则表达式

1 re匹配示例

# -*- coding:UTF8 -*-
import re

#查找匹配
text="验证码是安全的"
pattern = re.compile(r'密码|验证码|安全')
result = re.findall(pattern,text)  #得到的是['验证码', '安全']

text="流量比较小"
pattern = re.compile(r'流量.*[少低高小]|(简历量|曝光量|浏览量).*[少低高多大]')#两种匹配模式,通过|分开,其中()中的内容是或的关系,[]中的内容是任意一个,.*匹配无限多个任意字符
ret = re.search(pattern, text)#ret.group(0)表示匹配的整个句子,group是针对()来说的,第一个括号就是group(1),以此类推
print(ret.group(0))#流量比较小

text1="但是曝光量很高"
ret = re.search(pattern, text1)
print(ret.group(1))#但是曝光量很高

#分割字符串
text=r'one1two2three3four4five5'
pattern = re.compile(r'\d+')
result = re.split(pattern, text)#['one', 'two', 'three', 'four', 'five', '']

#替换
text=r'流量比较小有人访问'
pattern = re.compile(r'')
result = re.sub(pattern, ',但是',text)#流量比较,但是有人访问
print(result)

 

2单字符匹配规则

字符   功能
匹配任意1个字符(除了\n)
[] 匹配[]中列举的字符,列举的字符或的关系;一些特殊字符变为普通字符,比如*是普通的*,没有特殊含义
\d 匹配数字,也就是0-9
\D 匹配非数字,也就是匹配不是数字的字符
\s 匹配空白符,也就是 空格\tab
\S 匹配非空白符,\s取反
\w 匹配单词字符, a-z, A-Z, 0-9, _
\W 匹配非单词字符, \w取反
^ 匹配字符串的开头。如"^(http:).*",匹配以http:开头的字符串
$ 匹配字符串的末尾。如".*(.com)$",匹配以.com结尾的字符串
|

或的关系。比如 C|cat 表示的是 C或cat; 如果要表示Cat或cat,则应该写为 (C|c)at。

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 


3 表示数量的规则

字符  功能
* 匹配前一个字符出现0次多次或者无限次,可有可无,可多可少
+ 匹配前一个字符出现1次多次或则无限次,直到出现一次
?   匹配前一个字符出现1次或者0次,要么有1次,要么没有
{m} 匹配前一个字符出现m次
{m,}  匹配前一个字符至少出现m次
{m,n}  匹配前一个字符出现m到n次
.* 贪婪匹配,就是尽可能多的匹配
.*? 非贪婪匹配,只要满足要求,就停止。

 

 

 

 

 

 

 

 

 

 

 

 

 

4 分组与捕获

  • (exp)    :分组,并捕获该分组匹配到的文本
  • (?:exp) :分组,但不捕获该分组匹配到的文本

(exp) :把括号内的正则作为一个分组,系统自动分配组号,可以通过分组号引用该分组;

(?P<name>exp) :定义一个命名分组,分组的正则是exp,系统为该分组分配分组号,可以通过分组名或分组号引用该分组;

(?:exp) :定义一个不捕获分组,该分组只在当前位置匹配文本,在该分组之后,无法引用该分组,因为该分组没有分组名,没有分组号,也不会占用分组编号;

字符 

描述

示例

(?:pattern)

匹配pattern,但不捕获匹配结果。

'industr(?:y|ies)

匹配'industry'或'industries'。

(?=pattern)

零宽度正向预查,不捕获匹配结果。

'Windows (?=95|98|NT|2000)'

匹配 "Windows2000" 中的 "Windows"

不匹配 "Windows3.1" 中的 "Windows"。

(?!pattern)

零宽度负向预查,不捕获匹配结果。

'Windows (?!95|98|NT|2000)'

匹配 "Windows3.1" 中的 "Windows"

不匹配 "Windows2000" 中的 "Windows"。

(?<=pattern)

零宽度正向回查,不捕获匹配结果。

'2000 (?<=Office|Word|Excel)'

匹配 " Office2000" 中的 "2000"

不匹配 "Windows2000" 中的 "2000"。

(?<!pattern)

零宽度负向回查,不捕获匹配结果。

'2000 (?<!Office|Word|Excel)'

匹配 " Windows2000" 中的 "2000"

不匹配 " Office2000" 中的 "2000"。

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

5 高效表达式建议

(1)每使用一个普通括号()而不是非捕获型括号(?:…),就会保留一部分内存等着你再次访问。这样的正则表达式、无限次地运行次数,无异于一根根稻草的堆加,终于能将骆驼压死。养成合理使用(?:…)括号的习惯。

(2)将一条复杂的正则表达式拆分为两条或多条简单的正则表达式,编程难度会降低,运行效率会提升。

(3)在适当的时候用上^,$,\b等等定位锚点,能有效提升找到成功匹配、淘汰不成功匹配的效率。

(4)在 Java 中使用正则表达式的时候我们需要先编译,所以应该尽量重用我们已经定义的正则表达式。

 

参考:《精通正则表达式》第5章、第6章

     https://www.cnblogs.com/wuhong/archive/2011/02/18/1957017.html

posted @ 2019-11-01 14:18  suwenyuan  阅读(285)  评论(0编辑  收藏  举报