正则表达式和re模块

了解正则表达式

正则表达式是对字符串操作的一种逻辑公式,用事先定义好的一些特殊字符,及这些特定字符的组合,组成一个“规则字符串”,这个“规则字符串”用来表达对字符的一种过滤逻辑。正则表达式是用来匹配字符串的强大工具,python中的re模块封装了正则表达式的功能。

一般字符

.(点)匹配除换行符“\n”以外的任意字符

\转义字符,改变特殊意义的元字符,使其变成普通字符

[……]匹配字符组中的字符

[^……]匹配除了字符组中字符的所有字符

\d 等价于匹配[0-9]匹配0-9的数字

\D等价于匹配[^0-9]匹配非0-9的数字

\w等价于[A-Za-z0-9]匹配数字字母

\W等价于[^A-Za-z0-9]匹配非数字字母下划线

\s匹配任意的空白符

\S匹配任意的非空白符

\n匹配一个换行符

\t匹配一个制表符

\b 匹配一个单词的结尾

a|b匹配字符串a或者b

()匹配括号内的表达式,也表示一个组

量词

?等价于匹配长度{0,1}零个或者一个

*等价于匹配长度{0,}零个或者多个

+等价于匹配长度{1,}一个或者多个

{n}重复n次

{n,}重复n次或更多次

{n,m}重复n到m次

边界匹配

^匹配字符串的开始,在多行模式中匹配每一行的开头

$匹配字符串的结尾,在多行模式中匹配每一行的结尾

\A仅匹配字符串的开始如:\Aabc

\Z仅匹配字符串的末尾如:abc\Z

逻辑、分组

a|b匹配字符串a或者b,顺序从左到右,一旦匹配就逃过右边的表达式。

(……)括起来的表达式将作为分组,可以后接量词。表达式中的|仅在该组中生效。

(?P<name>)分组,除了原有的编号外再指定一个额外的别名。

\<number>引用编号为<number>的分组匹配的字符串。

(?P=name)引用别名为<name>的分组匹配到的字符串。

 

贪婪与非贪婪

贪婪与非贪婪模式影响的是被量词修饰的子表达式的匹配行为,贪婪模式在整个表达式匹配成功的前提下,尽可能多的匹配(python中的数量词默认是贪婪的),而非贪婪模式在整个表达式匹配成功的前提下,尽可能少得匹配。

*?,+?,??,{m,n}?, {m,}? 转为非贪婪模式(尽可能少得匹配)

转义符号\

在python中,使用原生字符串r可以解决所有的转义符号歧义或者漏写,比如r"\d"r"\w"等

正则表达式的示例应用

1.验证用户名和密码:("^[a-zA-Z]\w{5,15}$")正确格式:"[A-Z][a-z]_[0-9]"组成,并且第一个字必须为字母6~16位;
2.验证电话号码:("^(\d{3,4}-)\d{7,8}$")正确格式:xxx/xxxx-xxxxxxx/xxxxxxxx;
3.验证手机号码:"^1[3|4|5|7|8][0-9]{9}$";
4.验证身份证号(15位或18位数字):"\d{14}[[0-9],0-9xX]";
5.验证Email地址:("^\w+([-+.]\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*$");
6.只能输入由数字和26个英文字母组成的字符串:("^[A-Za-z0-9]+$");
7.整数或者小数:^[0-9]+([.][0-9]+){0,1}$
8.只能输入数字:"^[0-9]*$"。
9.只能输入n位的数字:"^\d{n}$"。
10.只能输入至少n位的数字:"^\d{n,}$"。
11.只能输入m~n位的数字:"^\d{m,n}$"。
12.只能输入零和非零开头的数字:"^(0|[1-9][0-9]*)$"。
13.只能输入有两位小数的正实数:"^[0-9]+(\.[0-9]{2})?$"。
14.只能输入有1~3位小数的正实数:"^[0-9]+(\.[0-9]{1,3})?$"。
15.只能输入非零的正整数:"^\+?[1-9][0-9]*$"。
16.只能输入非零的负整数:"^\-[1-9][0-9]*$"。
17.只能输入长度为3的字符:"^.{3}$"。
18.只能输入由26个英文字母组成的字符串:"^[A-Za-z]+$"。
19.只能输入由26个大写英文字母组成的字符串:"^[A-Z]+$"。
20.只能输入由26个小写英文字母组成的字符串:"^[a-z]+$"。
21.验证是否含有^%&',;=?$\"等字符:"[%&',;=?$\\^]+"。
22.只能输入汉字:"^[\u4e00-\u9fa5]{0,}$"。
23.验证URL:"^http://([\w-]+\.)+[\w-]+(/[\w-./?%&=]*)?$"。
24.验证一年的12个月:"^(0?[1-9]|1[0-2])$"正确格式为:"01"~"09"和"10"~"12"。
25.验证一个月的31天:"^((0?[1-9])|((1|2)[0-9])|30|31)$"正确格式为;"01"~"09"、"10"~"29"和“30”~“31”。
26.获取日期正则表达式:\\d{4}[年|\-|\.]\d{\1-\12}[月|\-|\.]\d{\1-\31}日?
评注:可用来匹配大多数年月日信息。
27.匹配空白行的正则表达式:\n\s*\r
28.匹配首尾空白字符的正则表达式:^\s*|\s*$
评注:可以用来删除行首行尾的空白字符(包括空格、制表符、换页符等等),非常有用的表达式
29.匹配ip地址:([1-9]{1,3}\.){3}[1-9]。
评注:提取ip地址时有用
 
python中的RE模块

python中自带了re模块,它提供了对正则表达式的支持。
import re

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

ret = re.search('a', 'eva egon yuan').group()
print(ret) #结果 : 'a'
# 函数会在字符串内查找模式匹配,只到找到第一个匹配然后返回一个包含匹配信息的对象,该对象可以
# 通过调用group()方法得到匹配的字符串,如果字符串没有匹配,则返回None。

ret = re.match('a', 'abc').group()  # 同search,不过仅在字符串开始处进行匹配,失败则返回None
print(ret)
#结果 : 'a'

#指定格式切分,返回列表
print(re.split('\d+','one1two2three3four4'))#不保留匹配的项
#结果为:['one', 'two', 'three', 'four', '']
print(re.split('\d+','one1two2three3four4')#加上括号后保留了匹配的项

['one', '1', 'two', '2', 'three', '3', 'four', '4', '']

#
替换匹配到的字符串并返回替换后的结果 ret = re.sub('\d', 'H', 'eva3egon4yuan4', 1)#将数字替换成'H',参数1表示只替换1个 print(ret) #evaHegon4yuan4 ret = re.subn('\d', 'H', 'eva3egon4yuan4')#将数字替换成'H',返回元组(替换的结果,替换了多少次) print(ret) #finditer 返回一个存放匹配结果的迭代器 ret = re.finditer("\d",'ds3sy4784a') print(ret)#<callable_iterator object at 0x02A013B0> print(next(ret).group())#3 print(next(ret).group())#4

findall的优先级

ret = re.findall("www.(baidu|oldboy).com","www.oldboy.com")
print(ret)#['oldboy'] 优先将括号内的内容返回
ret = re.findall("www.(?:baidu|oldboy).com","www.oldboy.com")
print(ret)#['www.oldboy.com']?号取消优先

练习

ret = re.search("<(?P<tag_name>\w+)>\w+</(?P=tag_name)>","<h1>hello</h1>")
#可以在分组中利用?<name>的形式给分组起名字,
#获取的结果可以直接用group(“名字”拿到对应的值)
print(ret.group("tag_name"))#h1
print(ret.group())#<h1>hello</h1>

ret = re.search(r"<(\w+)>\w+</\1>","<h1>hello</h1>")
#如果不给分组起名,也可以用\序号来找到对应的组,表示要找的内容和前面组的内容一致
#获取的匹配结果可以直接用group(序号)拿到对应的值
print(ret.group(1))#h1
print(ret.group())#<h1>hello</h1>
匹配标签
print(re.findall(r"\d+","1-2*(60+(-40.35/5)-(-4*3))"))
#['1', '2', '60', '40', '35', '5', '4', '3']
print(re.findall(r"-?\d+\.\d*|(-?\d+)","1-2*(60+(-40.35/5)-(-4*3))"))
#只显示括号里面的内容,即使|前面的表达式匹配到了也不会显示,会出现一个空的字符串
#['1', '-2', '60', '', '5', '-4', '3']
ret.remove("")
print(ret) #['1', '-2', '60', '5', '-4', '3']#利用remove去除空的字符串
匹配整数

 

 

 

 

 


posted on 2017-08-08 18:51  keepDoing  阅读(182)  评论(0编辑  收藏  举报

导航