什么是正則表達(dá)式
世界上信息非常多,而我們關(guān)注的信息有限。假如我們希望只提取出關(guān)
注的數(shù)據(jù),此時(shí)可以通過(guò)一些表達(dá)式進(jìn)行提取,正則表達(dá)式就是其中一
種進(jìn)行數(shù)據(jù)篩選的表達(dá)式。
原子
原子是正則表達(dá)式中最基本的組成單位,每個(gè)正則表達(dá)式中至少要包含
一個(gè)原子。常見(jiàn)的原子類(lèi)型有:
- a普通字符作為原子
- b非打印字符作為原子
- c通用字符作為原子
- d原子表
正則表達(dá)式函數(shù)
正則表達(dá)式函數(shù)有re.match()函數(shù)、re.search()函數(shù)、全局匹配函數(shù)、 re.sub()函數(shù)。
re.search
re.search 掃描整個(gè)字符串并返回第一個(gè)成功的匹配。
import re
pat = "yue"
string = "http://iqianyue.com"
result = re.search(pat,string)
print(result)
輸出結(jié)果如下:
<_sre.SRE_Match object; span=(12, 15), match='yue'>
re.match
re.match 嘗試從字符串的起始位置匹配一個(gè)模式,如果不是起始位置匹配成功的話(huà),match()就返回none。
import re
pat = "yue"
string = "yuehttp://iqyueianyue.com"
result = re.match(pat,string)
print(result)
輸出結(jié)果如下:
<_sre.SRE_Match object; span=(0, 3), match='yue'>
全局匹配函數(shù) re.compile().findall():
掃描整個(gè)字符串并以列表的形式返回符合條件的匹配值
import re
pat = "p.*?n"
string = "abcpythonjgkhappynn"
result = re.compile(pat).findall(string)
print(result)
輸出結(jié)果如下:
['python', 'ppyn']
re.match與re.search的區(qū)別
re.match只匹配字符串的開(kāi)始,如果字符串開(kāi)始不符合正則表達(dá)式,則匹配失敗,函數(shù)返回None;而re.search匹配整個(gè)字符串,直到找到一個(gè)匹配。
模式修正符
所謂模式修正符,即可以在不改變正則表達(dá)式的情況下,通過(guò)模式修正符改變正則表達(dá)式的含義,從而實(shí)現(xiàn)一些匹配結(jié)果的調(diào)整等功能。
正則表達(dá)式中常用的模式修正符有i、g、m、s、x、e等。它們之間可以組合搭配使用。
- 修正符:i不區(qū)分大小寫(xiě)的匹配;
- 修正符:m將字符串視為多行,不管是那行都能匹配;
- 修正符:s將字符串視為單行,換行符作為普通字符;
- 修正符:x將模式中的空白忽略;
- 修正符:A強(qiáng)制從目標(biāo)字符串開(kāi)頭匹配;
- 修正符:D如果使用$限制結(jié)尾字符,則不允許結(jié)尾有換行;
- 修正符:U只匹配最近的一個(gè)字符串;不重復(fù)匹配;
舉例如下:
import re
pat = "bai"
string = "http://www.Baidu.com"
result = re.search(pat,string,re.I)#不區(qū)分大小寫(xiě)
print(result)
貪婪模式與懶惰模式
貪婪模式的核心點(diǎn)就是盡可能多的匹配,而懶惰模式的核心點(diǎn)就是盡可能少的匹配(更精確的定位)。
import re
pat1 = "p.*y"#貪婪模式(盡可能多的匹配)
pat2 = "p.*?y"#懶惰模式(盡可能少的匹配)
string = "abcpythonfghappy"
result1 = re.search(pat1,string)
result2 = re.search(pat2,string)
print(result1)
print(result2)
輸出結(jié)果如下:
<_sre.SRE_Match object; span=(3, 16), match='pythonfghappy'>
<_sre.SRE_Match object; span=(3, 5), match='py'>
正則表達(dá)式實(shí)例
實(shí)例 | 描述 |
---|---|
python | 匹配 "python" |
[Pp]ython | 匹配 "Python" 或 "python" |
rub[ye] | 匹配 "ruby" 或 "rube" |
[aeiou] | 匹配中括號(hào)內(nèi)的任意一個(gè)字母 |
[0-9] | 匹配任何數(shù)字。類(lèi)似于 [0123456789] |
[a-z] | 匹配任何小寫(xiě)字母 |
[A-Z] | 匹配任何大寫(xiě)字母 |
[a-zA-Z0-9] | 匹配任何字母及數(shù)字 |
[^aeiou] | 除了aeiou字母以外的所有字符 |
. | 匹配除 "\n" 之外的任何單個(gè)字符。要匹配包括 '\n' 在內(nèi)的任何字符,請(qǐng)使用象 '[.\n]' 的模式。 |
\d | 匹配一個(gè)數(shù)字字符。等價(jià)于 [0-9]。 |
\D | 匹配一個(gè)非數(shù)字字符。等價(jià)于 [^0-9]。 |
\s | 匹配任何空白字符,包括空格、制表符、換頁(yè)符等等。等價(jià)于 [ \f\n\r\t\v]。 |
\S | 匹配任何非空白字符。等價(jià)于 [^ \f\n\r\t\v]。 |
\w | 匹配包括下劃線的任何單詞字符。等價(jià)于'[A-Za-z0-9_]'。 |
\W | 匹配任何非單詞字符。等價(jià)于 '[^A-Za-z0-9_]'。 |
非打印字符
元字符 | 描述 |
---|---|
\cx | 匹配由x指明的控制字符。例如, \cM 匹配一個(gè) Control-M 或回車(chē)符。x 的值必須為 A-Z 或 a-z 之一。否則,將 c 視為一個(gè)原義的 'c' 字符。 |
\f | 匹配一個(gè)換頁(yè)符。等價(jià)于 \x0c 和 \cL。 |
\n | 匹配一個(gè)換行符。等價(jià)于 \x0a 和 \cJ。 |
\r | 匹配一個(gè)回車(chē)符。等價(jià)于 \x0d 和 \cM。 |
\s | 匹配任何空白字符,包括空格、制表符、換頁(yè)符等等。等價(jià)于 [ \f\n\r\t\v]。 |
\S | 匹配任何非空白字符。等價(jià)于 [^ \f\n\r\t\v]。 |
\t | 匹配一個(gè)制表符。等價(jià)于 \x09 和 \cI。 |
\v | 匹配一個(gè)垂直制表符。等價(jià)于 \x0b 和 \cK。 |
特殊字符
特別字符 | 描述 |
---|---|
$ | 匹配輸入字符串的結(jié)尾位置。如果設(shè)置了 RegExp 對(duì)象的 Multiline 屬性,則 $ 也匹配 '\n' 或 '\r'。要匹配 $ 字符本身,請(qǐng)使用 $。 |
( ) | 標(biāo)記一個(gè)子表達(dá)式的開(kāi)始和結(jié)束位置。子表達(dá)式可以獲取供以后使用。要匹配這些字符,請(qǐng)使用 \( 和 \)。 |
* | 匹配前面的子表達(dá)式零次或多次。要匹配 * 字符,請(qǐng)使用 \*。 |
+ | 匹配前面的子表達(dá)式一次或多次。要匹配 + 字符,請(qǐng)使用 \+。 |
. | 匹配除換行符 \n 之外的任何單字符。要匹配 . ,請(qǐng)使用 \. 。 |
[ | 標(biāo)記一個(gè)中括號(hào)表達(dá)式的開(kāi)始。要匹配 [,請(qǐng)使用 \[。 |
? | 匹配前面的子表達(dá)式零次或一次,或指明一個(gè)非貪婪限定符。要匹配 ? 字符,請(qǐng)使用 \?。 |
\ | 將下一個(gè)字符標(biāo)記為或特殊字符、或原義字符、或向后引用、或八進(jìn)制轉(zhuǎn)義符。例如, 'n' 匹配字符 'n'。'\n' 匹配換行符。序列 '\' 匹配 "",而 '(' 則匹配 "("。 |
^ | 匹配輸入字符串的開(kāi)始位置,除非在方括號(hào)表達(dá)式中使用,此時(shí)它表示不接受該字符集合。要匹配 ^ 字符本身,請(qǐng)使用 \^。 |
{ | 標(biāo)記限定符表達(dá)式的開(kāi)始。要匹配 {,請(qǐng)使用 \{。 |
指明兩項(xiàng)之間的一個(gè)選擇。 |
限定符
字符 | 描述 |
---|---|
* | 匹配前面的子表達(dá)式零次或多次。例如,zo* 能匹配 "z" 以及 "zoo"。* 等價(jià)于{0,}。 |
+ | 匹配前面的子表達(dá)式一次或多次。例如,'zo+' 能匹配 "zo" 以及 "zoo",但不能匹配 "z"。+ 等價(jià)于 {1,}。 |
? | 匹配前面的子表達(dá)式零次或一次。例如,"do(es)?" 可以匹配 "do" 、 "does" 中的 "does" 、 "doxy" 中的 "do" 。? 等價(jià)于 {0,1}。 |
{n} | n 是一個(gè)非負(fù)整數(shù)。匹配確定的 n 次。例如,'o{2}' 不能匹配 "Bob" 中的 'o',但是能匹配 "food" 中的兩個(gè) o。 |
{n,} | n 是一個(gè)非負(fù)整數(shù)。至少匹配n 次。例如,'o{2,}' 不能匹配 "Bob" 中的 'o',但能匹配 "foooood" 中的所有 o。'o{1,}' 等價(jià)于 'o+'。'o{0,}' 則等價(jià)于 'o*'。 |
{n,m} | m 和 n 均為非負(fù)整數(shù),其中n <= m。最少匹配 n 次且最多匹配 m 次。例如,"o{1,3}" 將匹配 "fooooood" 中的前三個(gè) o。'o{0,1}' 等價(jià)于 'o?'。請(qǐng)注意在逗號(hào)和兩個(gè)數(shù)之間不能有空格。 |
python中正則表達(dá)式常用場(chǎng)景
- 匹配.com或.cn網(wǎng)址
import re
pat = "[a-zA-Z]+://[^\s]+[.com|.cn]"
string = '<a
result = re.compile(pat).findall(string)
print(result)
輸出如下:
['http://www.baidu.com']
- 匹配JavaScript帶標(biāo)簽的網(wǎng)址
比如從 https://read.douban.com/provider/all中將所有出版社提取出來(lái),把無(wú)關(guān)信息過(guò)濾掉。<div class="name">北京師范大學(xué)出版社</div>
import urllib
import re
# <div class="name">北京師范大學(xué)出版社</div>
url = "https://read.douban.com/provider/all"
pat = '<div class="name">(.*?)</div>'
data = urllib.request.urlopen(url).read().decode("utf-8","ignore")
result = re.compile(pat).findall(data)
print(result)
輸出結(jié)果如下:
['博集天卷', '北京郵電大學(xué)出版社', '北京師范大學(xué)出版社', '百花洲文藝出版社', '百花文藝出版社', '長(zhǎng)江數(shù)字', '重慶大學(xué)出版社', '東方文萃', '讀客圖書(shū)', '電子工業(yè)出版社', '當(dāng)代中國(guó)出版社', '第一財(cái)經(jīng)周刊', '豆瓣閱讀同文館', '豆瓣', '豆瓣閱讀', '豆瓣閱讀出版計(jì)劃', '東方巴別塔文化', '鳳凰壹力', '鳳凰悅世泓文', '鳳凰聯(lián)動(dòng)', 'Fiberead', '復(fù)旦大學(xué)出版社', '鳳凰雪漫', '果殼閱讀', '果麥文化', '廣西師范大學(xué)出版社', '杭州藍(lán)獅子文化創(chuàng)意股份有限公司', '后浪出版公司', '華東師范大學(xué)出版社', '華章數(shù)媒', '漢唐陽(yáng)光', '華文時(shí)代', '湖北人民出版社', '華章同人', '華夏盛軒', '海豚出版社', '虹膜出版', '化學(xué)工業(yè)出版社', '華中科技大學(xué)出版社', '湖北科學(xué)技術(shù)出版社', '黑龍江北方文藝出版社', '華文經(jīng)典', 'HarperCollins', '聚石文華', '金城出版社', '簡(jiǎn)書(shū)', '今古傳奇', '江蘇人民出版社', '九州幻想', '科幻世界', '酷威文化', '理想國(guó)', '漓江出版社', '磨鐵數(shù)盟', '寧波出版社', '南方人物周刊', 'ONE·一個(gè)', '浦睿文化', 'Parkstone International', 'Packt Publishing', '清華大學(xué)出版社', '青島出版社', '《人物》雜志', '人民文學(xué)出版社', '人民郵電出版社', '儒意欣欣', '人民東方出版?zhèn)髅?, '人民文學(xué)雜志社', '上海九久讀書(shū)人', '世紀(jì)文景', '四川數(shù)字出版?zhèn)髅接邢薰?, '上海譯文出版社', '時(shí)代華文', '上海雅眾文化', '世紀(jì)文睿', '時(shí)代華語(yǔ)', '商務(wù)印書(shū)館', '生活·讀書(shū)·新知三聯(lián)書(shū)店', '上海社會(huì)科學(xué)院出版社', '社會(huì)科學(xué)文獻(xiàn)出版社', '山西春秋電子音像出版社', '時(shí)代數(shù)聯(lián)', '陜西人民出版北京分公司', '《書(shū)城》雜志', '世圖北京', '四川文藝出版社', '上海文藝出版社', '上海人民出版社', '上海交通大學(xué)出版社', '斯坦威圖書(shū)', '上海人民美術(shù)出版社', '圖靈社區(qū)', 'Trajectory', '武漢大學(xué)出版社北京分社', '萬(wàn)有圖書(shū)', '我和豆瓣', '新經(jīng)典文化電子書(shū)', '新星出版社', '新華先鋒文化傳媒', '雪球', '懸疑世界', '現(xiàn)代出版社', '西南財(cái)經(jīng)大學(xué)出版社', '新華出版社', '新華先鋒出版科技', '譯林出版社', '譯言·東西文庫(kù)', '譯言·古登堡計(jì)劃', '悅讀紀(jì)', '陽(yáng)光博客', '悅讀名品', '燕山出版社', '閱文集團(tuán)華文天下', '中信出版社', '中國(guó)人民大學(xué)出版社', '中作華文', '中國(guó)輕工業(yè)出版社', '紫圖圖書(shū)', '浙版數(shù)媒', '中央編譯出版社', '知乎', '中國(guó)國(guó)家地理圖書(shū)部', '浙江攝影出版社', '中國(guó)經(jīng)濟(jì)出版社', '中國(guó)青年出版社', '中國(guó)民主法制出版社', '中國(guó)傳媒大學(xué)出版社', '中國(guó)言實(shí)出版社', '浙江大學(xué)出版社', '湛廬文化', '浙江文藝出版社', '中華書(shū)局']