簡介
正規表達式是一種描述字元的一種方式,通過該方式,比對字元串。
正規表達式是自由的,一個字元的含義往往代表着一類字元,通過多個正則正則符号的組合描述,可以使組成的正規表達式能夠描述一類字元串。
在開發中,很多時候使用正規表達式描述一類字元串。
注:正則在程式設計中是通用的
在python中,使用re子產品的match方法進行字元串與正則的比對。文法如下:
re.match(pattern, string, flags=0)
複制
- pattern:正規表達式
- string:需要進行比對的字元串
- flags:正規表達式的比對方式
比對成功傳回比對的對象,否則傳回None。
正則基本使用
最簡單的硬比對
使用re子產品前必須引入re,随後使用match方法進行正則比對:
import re
res = re.match("這是正則區域","這是正則區域")
print(res.group())
複制
以上代碼正則區域進行了比較硬核的比對,直接用 這是正則區域 作為正則比對,字元串内容也是 這是正則區域。比對完後把比對結果賦給res 變量,随後使用print輸出(group方法會可以提取資料)。結果如下:
在這裡插入圖檔描述
成功輸出了比對的内容。
接下來我把 這是正則區域 的字元串内容改為 這是字元串區域:
res = re.match("這是正則區域","這是字元串區域")
複制
結果如下:
在這裡插入圖檔描述
由于比對的值為None,是以輸出錯誤。我們可以更改為如下方法:
import re
res = re.match("這是正則區域","這是字元串區域")
if res:
print(res.group())
複制
這個時候就不會報錯了,沒有比對就不會輸出。
硬核的比對方式學完了,接下來學一點别的方式。
\d
先介紹一個符号 \d,\d 可以比對0-9的數字,在代碼中可以寫成如下形式:
import re
res = re.match("\d","2")
if res:
print(res.group())
複制
結果如下:
在這裡插入圖檔描述
如果後面的字元串為2則會比對2,如果把2更換成字母則将不會輸出任何值:
res = re.match("\d","a")
複制
結果如下:
在這裡插入圖檔描述
我們的代碼還可以更加複雜一點,當然隻是一點點不是億點點:
res = re.match("今天星期\d","今天星期3")
複制
這個時候不管是星期幾,隻要是數字都将會輸出顯示:
在這裡插入圖檔描述
[]
接下來認識一下[],[]可以比對方括号中列舉的字元。例如在[]中列舉1234,代碼寫為 1234,代碼如下:
import re
res = re.match("今天星期[0123456789]","今天星期3")
if res:
print(res.group())
複制
以上代碼是否還會比對成功輸出結果呢?當然是可以的,因為方括号中列舉了0-9這幾個數,并不是一些讀者認為的0123456789是一個整體,這一串數字是以字元單個存在說明,并非整體,是以肯定會比對成功并且顯示:
在這裡插入圖檔描述
以上代碼列舉了0-9這幾個數字,寫太長太過麻煩,可以寫成以下形式,友善快捷且清晰:
res = re.match("今天星期[0-9]","今天星期3")
複制
如果想列舉字母a-z也沒必要寫太長,例如:
res = re.match("今天星期[a-z]","今天星期t")
複制
結果如下:
在這裡插入圖檔描述
如果你想大寫也比對呢?這個很簡單,看如下示例:
res = re.match("今天星期[a-zA-Z]","今天星期T")
複制
因為方括号裡面的字元都是單個存在的,a-z描述的是a到z的字母,A-Z描述的是大寫A到Z的字母,是一個整體,是以直接寫成如上方式肯定是沒問題的。
結果如下:
在這裡插入圖檔描述
\w 與 \W
\w可以比對 A-Z、a-z、0-9和下劃線_。
\W可以比對 非字母、非數字、非下劃線以及非漢字,也就是和 \w反過來。
首先看\w:
import re
res = re.match("\w","a")
if res:
print(res.group())
複制
由于\w是比對 A-Z、a-z、0-9和下劃線_是以比對沒問題,結果如下:
在這裡插入圖檔描述
其它比對将不再列出,都是一個意思。
嘗試\W:
res = re.match("\W","+")
複制
結果ok:
在這裡插入圖檔描述
*、+、{}與?
進行到這如果還不增加一點難度想必就無趣了,現在開始使用一些字元對已學的單個字元比對進行描述,使正規表達式能夠比對多個字元。
現在有一個字元串 房價租金1999 如何進行正則比對?檢視代碼:
import re
res = re.match(r"房價租金[0-9]*","房價租金1999")
if res:
print(res.group())
複制
仔細看,正規表達式
房價租金[0-9]*
,前面的 房價租金 硬比對了房價租金這幾個字元串,之後我使用了一個中括号,裡面的内容為比對 0-9 其中任意一個數字,在一般情況下 0-9 比對隻能比對一個,我在方括号後面增加了一個 *号。
*号的作用是描述它前面的一個正規表達式 0-9 比對0次或者無限次,這裡出現了1次,則比對成功。結果如下:
在這裡插入圖檔描述
當然0次也可以的,我們把代碼更改為如下:
res = re.match("房價租金1*","房價租金")
複制
以上代碼使用号去比對1這個字元,如果不存在,正規表達式依舊會傳回比對對象,因為前面已經比對成功了。号0次沒有也ok,是以依舊會輸出:
在這裡插入圖檔描述
如果把以上代碼中的 * 号改為 + 号會出現什麼情況?我們試一下:
res = re.match("房價租金1+","房價租金")
複制
這時候将不會輸出。+号表示前面的字元出現1次,為0可不行,那麼我們比對一下 房價租金1111 這個字元串看看效果:
res = re.match("房價租金1+","房價租金111111111")
複制
結果如下:
在這裡插入圖檔描述
那如果我想比對固定次數如何?
這個時候就可以使用{}進行限定次數的比對:
res = re.match("房價租金1{0}","房價租金111111111")
複制
結果為:
在這裡插入圖檔描述
當然代碼也可以寫成:
res = re.match("房價租金1{0,4}","房價租金111111111")
複制
{0,4}中0為比對的起始位置,4為結束位置,如果4這個結束位置不填,那麼将會從0起始位置(其實位置可以寫任意位置,如1,2,3...)比對到無限次。
^與$
^表示從字元串頭進行比對,$表示配字元串結束。
現在開始來一個綜合的挑戰,比對一個郵箱位址吧,這個在正常的需求中也是很常見的:
import re
res = re.match("^\d+@\w+\.\w+",r"[email protected]")
if res:
print(res.group())
複制
檢視正則我們寫為:
^\d+@\w+.\w+
我們分解一下正規表達式的組成:
-
:在最開頭使用了一個^描述之後的一個正則描述為字元串開頭。\d為數字,+号為比對至少一個。連起來就是在字元串開頭比對一串數字。^\d+
-
@\w+
:一串數字結束後,硬比對一個@符号,郵箱都這樣。之後\w表示比對
A-Z、a-z、0-9和下劃線_(下劃線我不懂,不過好像我見過有吧),由于郵箱有qq郵箱,163郵箱,谷歌等不同的郵箱,是以我就用\w了。由于比對的不止一個,是以我用了+号進行之前的正則描述。
-
:最後進行了一個點 . 的硬比對,在 . 前面加了一個\是因為需要轉義,之後再比對一個 \w,然後完事。 結果如下:、.\w+
在這裡插入圖檔描述
讀者可以修改一下郵箱即可檢視效果。
注意:以上郵箱的比對形式并不是嚴謹的正則編寫方式,請勿在實際項目中使用,在這裡隻是為了友善示範,請見諒。
以上的基礎正則基本上在應用開發中已經夠用了,接下來再擴充一下正規表達式的符号。
|與()
| 為一個或運算,|符号左右兩邊的正則都可以進行比對,隻要有一個比對成功,那麼整個正則比對即為成功:
import re
re_1="^\d+@qq\.\w+"
re_2="^\d+@163\.\w+"
res = re.match(re_1+'|'+re_2,r"[email protected]")
if res:
print(res.group())
複制
在以上代碼中在上一個案例中修改,其中正則不再贅述,畢竟都相差不大。以上代碼中定義了兩個變量 re_1 與 re_2,re_1 為比對qq郵箱,re_2 為比對163的郵箱,在進行比對時,在正則中代碼編寫為
re_1+'|'+re_2
,使用 | 符号使左右兩邊連接配接,随後進行判斷。這個符号也就是或運算。結果如下:
在這裡插入圖檔描述
()圓括号的作用是進行分組:
import re
re_1="(^\d+)(@qq)(\.)(\w+)"
res = re.match(re_1,r"[email protected]")
if res:
print("0",res.group(0))
print("1",res.group(1))
print("2",res.group(2))
print("3",res.group(3))
print("4",res.group(4))
複制
以上代碼是上一個示例中修改,re_1 的變化不大,使用圓括号為每一個塊的正則分了組。之後使用group的時候傳入參數 0、1、2、3、4 。0表示正則比對出來的所有結果,1表示 (^\d+) 比對的結果,2表示 (@qq) 比對的結果,之後的序号以此類推。結果如下:
在這裡插入圖檔描述
爬蟲系列持續更新,歡迎關注、點贊、收藏。
下一篇将使用正則抓取房價。