python正则表达式学习
前言
最近在用django作一个功能,主要是为实现机器监控,这个过程中,涉及url识别IP路由问题,一开始用了各种表达方式都无法正确路由到IP,说明自己对这块还是有很多不熟悉的地方,本文主要是针对Python的正则表达式展开介绍,以作备忘。
Python正则介绍
正则匹配
学过Python的都知道,python中有一个正则表达式的模块: re. 正则匹配的模式主要有以下几类:
x? 匹配0个或1个x,最多1个
x+ 匹配1个或多个x,至少1个
x* 匹配0个或多个x
x{m,n} 匹配m与n之间个数的x,如{2,4},则可匹配到xx,xxx,xxxx
x|y 匹配x或y
^ 匹配文本开头
$ 匹配文本结尾
[a-zA-Z] 匹配26个字母的大小写
[^a-zA-Z] 匹配非26个字母的其它字符
[0-9] 匹配0-9之间的所有数字
\d 匹配数字
\D 不匹配数字
\w 匹配任意字母
\W 匹配任意除字母外的其它字符
\s 匹配空格
\S 不匹配空格
如果我要匹配一个邮件地址,该怎么做呢,我们先看下下面代码:
import re
x="[a-z]+@[a-z]+.[a-z]+"
s1='liran@devarea.com'
s2='liran#devarea.com'
c=re.match(x,s1)
if c:
print ('ok')
else:
print ('no')
先定义一个模式匹配串[a-z]+@[a-z]+.[a-z]+
, 这个模式串主要含义如下:
匹配一个字母组成的子串,至少1个字母组成 – [a-z]+
匹配一个符号 – @
匹配一个字母组成的子串,至少1个字母组成 – [a-z]+
匹配一个标点 – .
匹配一个字母组成的子串,至少1个字母组成 – [a-z]+
从上面可以看出,其它这个匹配方式是很简单的,可以匹配一些简单模式的邮件,如果邮件中包含数字和大写字母呢,也很简单,只要在匹配中加下数字的匹配就行,如下所示:
x="[a-zA-Z0-9]+@[a-zA-Z0-9]+.[a-zA-Z0-9]+"
如果要匹配特定后缀的邮件地址要如何呢,也比较简单,直接在模式串最后加特定后缀的子串就行,如我们要匹配.com,net之类的,我们可以如下方式来匹配:
x=[a-zA-Z0-9]+@[a-z0-9]+.(net|com)
还有一些更复杂的方式,如包含一些特殊字符的邮件地址,如下所示:
pattern="^[A-Za-z0-9\.\+_-]+@[A-Za-z0-9\._-]+\.[a-zA-Z]*$"
除了邮箱地址,我们经常需要去判断如电话号码,IP地址之类的,如下所示:
IP地址
ip="^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}$"
电话号码
phone = "'(\d{3}[-\.\s]??\d{3}[-\.\s]??\d{4}|\(\d{3}\)\s*\d{3}[-\.\s]??\d{4}|\d{3}[-\.\s]??\d{4})'"
还有可能是在爬虫时需要去匹配合归的URL链接,如下所示:
url='http[s]?://(?:[a-zA-Z]|[0-9]|[$-_@.&+]|[!*\(\),]|(?:%[0-9a-fA-F][0-9a-fA-F]))+'
正则查找
在实际Python应用中,我们也经常会用到正则查找功能,如查找文本中第一次出现的数字,可以如下用:
str = 'hello,this is 888, my first regular expression 999 exercise'
m = re.search(r"[0-9]+", str)
if m:
print('匹配: ',m.group()) #输出: 888
如果要匹配文本中所有数字呢,可以用findall
函数,如下所示:
str='hello,this is 888, my first regular expression 999 exercise'
m=re.findall(r"[0-9]+",str)
print m #输出: ['888','999']
所以用re还是很方便找到想要的子串的。
正则替换
在实际使用中,正则替换也是很常见,用re的sub函数
也能很方便解决。如我想把上面字符串中的数字全部替换成*,我们可以用如下方式来解决:
str = 'hello,this is 888, my first regular expression 999 exercise'
new_str = re.sub('[0-9]+', '*', str)
print new_str # 输出: hello,this is *, my first regular expression * exercise
如果要输出替换了多少处数字,可以用subn
函数,其返回一个两个元素的元组,第一个是替换后字符串,第二个是替换的次数,用法如下:
str='hello,this is 888, my first regular expression 999 exercise'
new_str = re.subn('[0-9]+','*',str)
print new_str #输出: ('hello,this is *, my first regular expression * exercise', 2)
正则分割
对于一个文本,如果我们想按指定子串将整个文件分割,可以用split
函数,返回一个列表,具体用法如下:
str = 'hello,this is 888, my first regular expression 999 exercise’
new_str = re.split('[0-9]+',str)
print new_str #输出: [ 'hello,this is ' , ', my first regular expression ' , ' exercise' ]
当然,如果用于分割的子串不固定,比如包含各种特殊字符,如下示例所示:
str = 'hello#,this is my&first$expression'
new_str = re.split('[#,&$]',str)
print new_str #输出: [ 'hello' , 'this is my' , 'first' , 'expression' ]
所以,只要掌握了分割模式,可以对文本进行任何处理,这在数据挖掘分析中也很用。
总结
python的正则用法还是很丰富的,如果能学好,在各个方面都很方便能解决实际问题。