py正则表达式笔记

一、定义
正则表达式是一个特殊的字符序列,它能帮助你方便的检查一个字符串是否与某种模式匹配。
re 模块使 Python 语言拥有全部的正则表达式功能。

二、Python字符匹配
>>> import re
>>> r=r'ab'
>>> print re.findall(r,'abcdefgabcd')
['ab', 'ab']
注意:如果有元字符,注意使用转义符'\'
e.g:
>>> r=r'1\*2'
>>> print re.findall(r,'1*2abd*1*2345')
['1*2', '1*2']
>>> r3=r'1\^123'
>>> print re.findall(r3,'1^12345')
['1^123']

三、Python元字符介绍
^ 匹配行首
>>> r2=r'^123'
>>> print re.findall(r2,'12345')
['123']

$ 匹配行尾
>>> r2=r'123$'
>>> print re.findall(r2,'12345123')
['123']

. 匹配单字符
>>> r=r'34.5'
>>> print re.findall(r,'345534523425')
['3455', '3425']

[] 匹配指定的一个字符集
1.
>>> r=r'a[a-zA-Z0-9]c'
>>> re.findall(r,'abcaBca9ccfg')
['abc', 'aBc', 'a9c']
2.
>>> r=r'[1a]'   #匹配1或a
>>> re.findall(r,'1ac11aac1acc')
['1', 'a', '1', '1', 'a', 'a', '1', 'a']

[^ ] 补集匹配不在区间范围内的字符,注意^放在前面
>>> r=r'a[^0-9]c'
>>> re.findall(r,'abcaBca9ccfg')
['abc', 'aBc']

四、Python特殊意义字符
\d 代表数字[0-9]
>>> r=r'a\dc'
>>> re.findall(r,'abcaBca9ccfg')
['a9c']

\D 非数字
>>> r=r'a\Dc'
>>> re.findall(r,'abcaBca9ccfg')
['abc', 'aBc']

\s 空白字符
>>> r=r'a\sc'
>>> re.findall(r,'a caBca9ccfg')
['a c']

\S 非空白字符
>>> r=r'a\Sc'
>>> re.findall(r,'a caBca9ccfg')
['aBc', 'a9c']

\w 单词字符[a-zA-Z0-9_]
>>> r=r'a\wc'
>>> re.findall(r,'abcaBca5ca*ca_c')
['abc', 'aBc', 'a5c', 'a_c']

\W 非单词字符
>>> r=r'a\Wc'
>>> re.findall(r,'abca*ca5ca ca#ca_c')
['a*c', 'a c', 'a#c']

{} 前一个字符的重复的次数:前一个字符在一个范围内的重复次数
1.
>>> r=r'a{2}c'
>>> re.findall(r,'aac,1ac,2aaaac')
['aac', 'aac']

2.
>>> r=r'a{1,3}c'
>>> re.findall(r,'ac,aac,aaac,aaaac')
['ac', 'aac', 'aaac', 'aaac']

* 将前一字符匹配大于等于0次,{0,}效果等价于*
>>> r=r'a*c'
>>> re.findall(r,'c,ac,aac,aaac')
['c', 'ac', 'aac', 'aaac']

+ 将前一字符匹配大于等于1次,{1,}效果等价于+
>>> r=r'a+c'
>>> re.findall(r,'ac,aac,abacc,aaac')
['ac', 'aac', 'ac', 'aaac']

>>> r=r'.+'  #.表示任意字符
>>> print re.findall(r,'welcome')
['welcome']

? 将前一字符匹配0次或1次,表示是否出现,{0,1}效果等价于?
>>> r=r'a?c'
>>> re.findall(r,'c,ac,aac,aaaac')
['c', 'ac', 'ac', 'ac']

*? 尽可能少的匹配
>>> r=r'ab*?'
>>> re.findall(r,'abbbbbbbbbb')
['a']

{m,n}  #多余拆分
>>> r=r'a{1,3}'
>>> re.findall(r,'a,aa,aaa,aaaa,aaaaa')
['a', 'aa', 'aaa', 'aaa', 'a', 'aaa', 'aa']

() 分组
>>> r=r'(.com.cn|.com|.cn)'
>>> re.findall(r,'123@qq.com,234@qq.com,345@qq.cn')
['.com', '.com', '.cn']

练习:
利用分组和特殊字符匹配邮箱,注意把'\.com\.cn'放在前面,整体加上括号作为一个大的分组处理方便看出来匹配到的是哪个
1.匹配qq邮箱
>>> r=r'\d{5,11}@qq.com'
>>> re.findall(r,'89753@qq.com,897530015@qq.com,212345@qq.com')
['89753@qq.com', '897530015@qq.com', '212345@qq.com']
===============================
>>> r=r'\d{5,11}@\w+.\w+'
>>> re.findall(r,'89753@qq.com,897530015@qq.com,212345@qq.com')
['89753@qq.com', '897530015@qq.com', '212345@qq.com']
======================================
>>> >>> r=r'\w+@\w+.\w+'
>>> re.findall(r,'89753@qq.com,897530015@qq.com,fangw1015@qq.com')
['89753@qq.com', '897530015@qq.com', 'fangw1015@qq.com']

2.
>>> r=r'(\w+@\w+(\.com\.cn|.com|.cn))'
>>> re.findall(r,'89753@qq.com,897530015@suncco.com.cn')
[('89753@qq.com', '.com'), ('897530015@suncco.com.cn', '.com.cn')]

五、Python正则常用函数
compile 编译后执行速度更快,findall 返回匹配列表
>>> r=r'a[bcd]e'
>>> p=re.compile(r)
>>> p.findall('abe,ace,ade,afe')
['abe', 'ace', 'ade']

match 匹配字符串开头,返回第一个匹配的内容
>>> r=r'(a[bcd]e)'
>>> res=re.match(r,'age,ace,ade,afe')
>>> print res.groups()

Traceback (most recent call last):
  File "<pyshell#25>", line 1, in <module>
    print res.groups()
AttributeError: 'NoneType' object has no attribute 'groups'
>>> res=re.match(r,'abe,ace,ade,afe')
>>> print res.groups()
('abe',)

search 匹配字符串全文,返回第一个匹配的内容
>>> r=r'(a[bcd]e)'
>>> res=re.search(r,'age,ace,ade,afe')
>>> print res.groups()
('ace',)

我们可以使用group(num)或 groups()匹配对象函数来获取匹配表达式。

group(num=0) 匹配的整个表达式的字符串;
group()可以一次输入多个组号,在这种情况下它将返回一个包含那些组所对应值的元组。

groups() 返回一个包含所有小组字符串的元组,从1到所含的小组号。

e.g:
>>> r=r'(a[bcd]e) or (a[def]g)'
>>> res=re.match(r,'abe or adg')
>>> print res.group()
abe or adg
>>> print res.group(1)
abe
>>> print res.group(2)
adg
>>> print res.group(1,2)
('abe', 'adg')
>>> print res.groups()
('abe', 'adg')

sub 字符串正则替换,返回替换字符串
1.
>>> re.sub(r'a..d','python','abcd,acd,namnd')
'python,acd,npython'

2.指定替换次数
>>> re.sub(r'a..d','python','abcd,acd,namnd',1)
'python,acd,namnd'

subn 字符串正则替换,返回元组(替换字符串,替换次数)
>>> re.subn(r'a..d','python','abcd,acd,namnd')
('python,acd,npython', 2)

split 返回切割后的列表
1.
>>> re.split(r'\+','12+34-56*78/90')
['12', '34-56*78/90']

2.
>>> re.split(r'[\+\-\*\/]','12+34-56*78/90')
['12', '34', '56', '78', '90']

应用:
1. 正则匹配身份证号
现在国家统一规定18位身份证:地址码(1+5)+ 出生日期码(8)+ 顺序码(3)+ 校验码X(1)-----------------------重庆市(500000)
>>> r=r'(^[1-8][0-7]{2}\d{3}[12]\d{3}(0[1-9]|1[012])(0[1-9]|[12]\d|3[01])\d{3}([0-9X])$)'
>>> print re.findall(r,'330726196507040016')
[('330726196507040016', '07', '04', '6')]
>>> print re.findall(r,'33070219630306041X')
[('33070219630306041X', '03', '06', 'X')]

2. 写一个网页爬虫,下载网页中的图片(下载用urllib.urlretrieve) ------------------------http://tieba.baidu.com/p/4114581614
e.g:
#coding=utf-8
import urllib,re,os
from selenium import webdriver

driver = webdriver.Firefox()

def init():
    driver.maximize_window()
    driver.get("http://tieba.baidu.com/p/4114581614")
    driver.set_page_load_timeout(60)
    
def crawler():
    content=driver.page_source
    reg=r'src="(http://imgsrc.baidu.com/forum/w.+?\.jpg)"'
    imglist=re.findall(reg,content)
    print imglist
    num=1
    for imgurl in imglist:
        print imgurl
        imgname = "%03d" % num
        urllib.urlretrieve(imgurl, "d:/py/img/food"+os.sep+str(imgname)+".jpg")
        num+=1
        
def drop():   
    driver.quit()
    
if __name__ == '__main__':
    init()
    crawler()
    drop()


  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值