友情提示:380元/半年,儿童学编程,就上码丁实验室。
可爱的小朋友们,今天我们一起来学习正则表达式吧~
首先呢,我们一般会在爬虫中常常用到正则表达式,因为需要发现网页之间的规律和图片链接之间的规律,然后按照内容特征来自动查找。然而正则表达式就是用来描述这些复杂规则的工具。
re模块的基本函数
Python的正则表达式的模块是 ‘re’,在每次使用的时候,要先导入。格式:import re
re模块的基本函数
(1)re.match(pattern, string, flags=0)#从字符串的起始位置开始匹配,若不是起始位置匹配成功,则返回none。
<1>参数分析:
pattern 正则表达式模式(描述的搜索规则)
string 要匹配的字符串。
flags 标志位,用于控制正则表达式的匹配方式,如:是否区分大小写,多行匹配等等。

(2)re.search(pattern, string, flags=0)#搜索整个字符串
(3)findall(string[, pos[, endpos]]) #搜索整个字符串,返回一个list
(4)使用 compile 加速
compile( rule [,flag] ) #第一个参数是规则式,第二个参数是规则选项。结果返回一个 Pattern 对象。
注意:直接使用 findall ( rule , target ) 的方式来匹配字符串,一次两次可以,如果要多次使用同一规则来进行匹配,建议使用 re.compile 函数来将规则预编译,然后使用返回的Pattern 对象来进行查找。
Pattern 对象方法:
findall ( targetString [, startPos [,endPos] ] )
match ( targetString [, startPos [,endPos] ] )
search ( targetString [, startPos [,endPos] ] )
范例:
> import re
'b','www.baidu.com') > re.findall(r
['b']
'w','www.baidu.com') > re.match(r
<_sre.SRE_Match object; span=(0, 1), match='w'>
'bai','www.baidu.com') > re.search(r
<_sre.SRE_Match object; span=(4, 7), match='bai'>
'[A-Z]') #如果需要多次查找正则表达式,可以先编译,然后进行其他的调用 > p=re.compile(r
'I love programming') #模式对象(由正则表达式编译过来的)的方法,少了一个参数,把待匹配字符串传进去即可 > p.search(
<_sre.SRE_Match object; span=(0, 1), match='I'>
'I love programming') > p.findall(
['I']
正则表达式模式语法中的特殊元素
模式 |
描述 |
^ |
匹配字符串的开头 |
$ |
匹配字符串的末尾 |
. |
匹配任意字符,除了换行符,当re.DOTALL标记被指定时,则可以匹配包括换行符的任意字符 |
[...] |
用来表示一组字符,单独列出:[amk] 匹配 ‘a’,’m’或’k’ |
[^...] |
不在[]中的字符:[^abc] 匹配除了a,b,c之外的字符 |
re* |
匹配0个或多个的表达式 |
re+ |
匹配1个或多个的表达式 |
re? |
匹配0个或1个由前面的正则表达式定义的片段,非贪婪方式 |
re{ n}/re{ n,} |
精确匹配n个前面表达式 |
re{ n, m} |
匹配 n 到 m 次由前面的正则表达式定义的片段,贪婪方式 |
a| b |
匹配a或b |
(re) |
对正则表达式分组并记住匹配的文本 |
(?#…) |
注释 |
w |
匹配字母数字及下划线 |
W |
匹配非字母数字及下划线 |
s |
匹配任意空白字符,等价于 [tnrf] |
S |
匹配任意非空字符 |
d |
匹配任意数字,等价于 [0-9] |
D |
匹配任意非数字 |
A |
匹配字符串开始 |
Z |
匹配字符串结束,如果是存在换行,只匹配到换行前的结束字符串 |
z |
匹配字符串结束 |
G |
匹配最后匹配完成的位置 |
b |
匹配一个单词边界,也就是指单词和空格间的位置。例如, ‘erb’ 可以匹配”never” 中的 ‘er’,但不能匹配 “verb” 中的 ‘er’ |
B |
匹配非单词边界。’erB’ 能匹配 “verb” 中的 ‘er’,但不能匹配 “never” 中的 ‘er’ |
n, t, 等 |
匹配一个换行符。匹配一个制表符 |
正则表达式实例
字符类
实例 |
描述 |
rub[ye] |
匹配 “ruby” 或 “rube” |
[aeiou] |
匹配中括号内的任意一个字母 |
[0-9] |
匹配任何数字。类似于 [0123456789] |
[a-z] |
匹配任何小写字母 |
[A-Z] |
匹配任何大写字母 |
[a-zA-Z0-9] |
匹配任何字母及数字 |
[^aeiou] |
除了aeiou字母以外的所有字符 |
[^0-9] |
匹配除了数字外的字符 |
特殊字符类
实例 |
描述 |
. |
匹配除 “n” 之外的任何单个字符。要匹配包括 ‘n’ 在内的任何字符,请使用象 ‘[.n]‘ 的模式。 |
d |
匹配一个数字字符。等价于 [0-9]。 |
D |
匹配一个非数字字符。等价于 [^0-9]。 |
s |
匹配任何空白字符,包括空格、制表符、换页符等等。等价于 [ fnrtv]。 |
S |
匹配任何非空白字符。等价于 [^ fnrtv]。 |
w |
匹配包括下划线的任何单词字符。等价于’[A-Za-z0-9_]‘。 |
W |
匹配任何非单词字符。等价于 ‘[^A-Za-z0-9_]‘。 |
范例:
r'[aeiou]','l love code') re.search(
<_sre.SRE_Match object; span=(3, 4), match='o'>
r'[a-z]','l love math') re.search(
<_sre.SRE_Match object; span=(0, 1), match='l'>
r'[0-9]','123 is 123') re.search(
<_sre.SRE_Match object; span=(0, 1), match='1'>
#限定匹配次数使用{}
r'bc{3,10}','bccccccd') re.search(
<_sre.SRE_Match object; span=(0, 7), match='bcccccc'>
#匹配0-255的这个范围里面的数字
r'[01]dd|2[0-4]d|25[0-5]','188') re.search(
<_sre.SRE_Match object; span=(0, 3), match='188'>
#小括号()是分组,一个小组是一个整体,重复3次。这里考虑数字的位数。{0,1}代表重复0次或者1次,可有可无
r'(([01]{0,1}d{0,1}d|2[0-4]d|25[0-5]).){3}([01]{0,1}d{0,1}d|2[0-4]d|25[0-5])','192.168.1.1') re.search(
<_sre.SRE_Match object; span=(0, 11), match='192.168.1.1'>
# |管道符,相当于逻辑或 ,如A|B 表示匹配正则表达式A或者B
>>> re.search(r'xiaoy(u|i)','xiaoyu')
<_sre.SRE_Match object; span=(0, 6), match='xiaoyu'>
#贪婪,在符号的条件下,会尽可能多的去匹配
"<html><tittle>i love programming</tittle></html>" s=
r'<.+>',s) re.search(
<_sre.SRE_Match object; span=(0, 48), match='<html><tittle>i love programming</tittle></html>'>
# .+?非贪婪
>>> re.search(r'<.+?>',s)
<_sre.SRE_Match object; span=(0, 6), match='<html>'>
常见需求表达式
1:数字:^[0-9]*$
2:m-n位的数字:^d{m,n}$
3:英文和数字:^[A-Za-z0-9]+$
4:由26个英文字母组成的字符串:^[A-Za-z]+$
5:由数字和26个英文字母组成的字符串:^[A-Za-z0-9]+$
6:身份证号(15位、18位数字):^d{15}|d{18}$
7:密码(以字母开头,长度在6~18之间,只能包含字母、数字和下划线):^[a-zA-Z]w{5,17}$
8:日期格式:^d{4}-d{1,2}-d{1,2}
9:IP地址:
(?:(?:[01]{0,1}d{0,1}d|2[0-4]d|25[0-5]).){3}(?:[01]{0,1}d{0,1}d|2[0-4]d|25[0-5])
正则表达式实例:自动获取代理ip地址
import urllib.request
import re
def open_url(url):
req=urllib.request.Request(url)
req.add_header('User-Agent','Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36')
page=urllib.request.urlopen(req)
html=page.read().decode('utf-8')
return html
def get_img(html):
p=r'(?:(?:[01]{0,1}d{0,1}d|2[0-4]d|25[0-5]).){3}(?:[01]{0,1}d{0,1}d|2[0-4]d|25[0-5])'
iplist=re.findall(p,html)
for each in iplist:
print(each)
if __name__=='__main__':
url="http://cn-proxy.com"
get_img(open_url(url))
#运行结果
====================== RESTART: F:/Pythondemo/get_ip.py ======================
183.146.213.56
121.40.60.55
183.146.213.157
119.41.236.180
101.231.104.82
39.105.229.23
39.137.168.23
117.127.16.20
39.137.168.23
117.191.11.72
60.9.1.81
36.25.243.50
101.4.136.34
222.74.237.24
121.40.162.23
THE END