Python之正則表達式基礎語法

微信公眾號:CodeId
有什么建議可以到公眾號里進行留言。

本篇文章主要介紹python有關正則表達式的使用。說到使用正則表達式,我們首先應該了解什么是正則表達式,簡單的說,正則表達式是一個描述字符串規則的代碼。比如說我們經常使用的郵箱:1234567@qq.com1234567@163.com…你會發現他們都有一定的規則,而這個規則的描述就涉及到具體的正則表達式語法了,下面我們就來了解一些基礎的語法:

1. 最簡單的正則表達式

最簡單的正則表達式其實就是普通字符串,它可以匹配其自身。
比如:正則表達式 'CodeId' 可以匹配字符串 CodeId

import re
result = re.search('CodeId','CodeId is very good')
print(result.group()) # CodeId

上述代碼是通過pythonre(正則表達式)模塊對正則表達式的一個使用,其中re.search()方法的作用就是對整個字符串進行搜索,并返回第一個匹配的字符串的匹配對象,匹配失敗會返回 None,它的語法是:
re.search(pattern, string, flags=0)

  • pattern:表示使用的正則表達式
  • string:表示要匹配的字符串
  • flags:用來控制正則表達式匹配規則的標志位

group()方法的作用是:返回匹配的一個或多個子字符串

2. 限制數量的表達式(限定符)

在講解限定符之前,先講解一下什么是貪婪模式非貪婪模式
貪婪模式:是盡可能多的匹配。限定符默認都是貪婪模式的。
非貪婪模式:是盡可能少的匹配。
比如我有一個書柜可以放1到100本書,貪婪模式就是放盡可能的接近或等于100本書,而非貪婪模式就是放盡可能的接近或等于1本書。
一、*:
作用:匹配前面的子表達式零次或者多次
比如:ab*它會匹配a,ab,abb或者a后面任意數量的b

import re
result1 = re.search('ab*','a')
print(result1.group()) # a
result2 = re.search('ab*','abbb')
print(result2.group()) # abbb

二、+:
作用:匹配前面的子表達式一次或者多次
比如:ab+它會匹配ab,abb,abb或者ab后面任意數量的b
注意*+的區別就是:+中的a后面至少有一個b,而*中的a后面可以沒有b

result1 = re.search('ab+','a')
print(result1) # None
result2 = re.search('ab+','abbb')
print(result2.group()) # abbb

三、?:
作用1:匹配前面的子表達式零次或者一次
比如:ab?可以匹配a或者ab

result1 = re.search('ab?','a')
print(result1.group()) # a
result2 = re.search('ab?','abbb')
print(result2.group()) # ab

作用2:指定限定符為非貪婪模式。
比如:ab*?匹配字符串abbb會返回a

 result1 = re.search('ab*','abbb')# 貪婪模式 
print(result1.group()) # abbb 
result2 = re.search('ab*?','abbb')# 非貪婪模式 
print(result2.group()) # a 
result3 = re.search('ab+','abbb')# 貪婪模式 
print(result3.group()) # abbb 
result4 = re.search('ab+?','abbb')# 非貪婪模式
print(result4.group()) # ab

四、{n}:
作用:對前面的子表達式重復n次,n是一個非負整數。
比如:Co{2}deId可以匹配CoodeId,但是不可以匹配CodeId

result = re.search('Co{2}deId','CoodeId')
print(result.group())# CoodeId
result = re.search('Co{2}deId','CodeId')
print(result) # None

五、{n,m}:
作用:對前面的子表達式重復nm次,n,m是一個非負整數并且n<=m。其中nm是可以省略其中一個。比如:

  • {n,}:表示對前面的子表達式至少重復n次。
  • {,m}:表示對前面的子表達式至多重復m次。
result = re.search('Co{2,}deId','CooodeId')
print(result.group())# CooodeId
result = re.search('Co{,2}deId','CodeId')
print(result.group()) # CodeId
result = re.search('Co{2,4}deId','CooodeId')
print(result.group()) # CooodeId

3.定位符號

定位符用來描述字符串或單詞的邊界。指定在字符串的什么位置開始匹配。
定位符號如下:
一、^:
作用1:匹配字符串開始的位置。如果是多行模式,還會與\n,\r的位置匹配。
比如:^CodeId會匹配CodeId,CodeIda,不會匹配aCodeId

result = re.search('^CodeId','CodeIda')
print(result.group()) # CodeId
result = re.search('^CodeId','aCodeIda')
print(result) # None
result = re.search('^CodeId','a\nCodeIda',re.MULTILINE) # 多行模式下 
print(result.group()) # CodeId

re.MULTILINE是設置為多行模式
作用2:^在方括號表達式中使用,表示的意思。
比如:[^1]表示匹配不是字符1

result = re.search('[1]','a1')
print(result.group()) # 1
result = re.search('[^1]','a1')
print(result.group()) # a

二、$:
作用:匹配字符串結尾的位置。如果是多行模式,還會與\n,\r的位置匹配。
比如:ab$會匹配cdab,asab

result = re.search('ab$','cdab')
print(result.group()) # ab
result = re.search('ab$','abcd')
print(result) # None

三、\b:
作用:匹配單詞的開始或結束的位置.
比如:ry\b就是匹配單詞中以ry結尾匹配項。\bis是匹配單詞中以is開始的匹配項

result = re.search(r'ry\b','CodeId is very good')
print(result.group()) # ry
result = re.search(r'\bis','CodeId is very good')
print(result.group()) # is
result = re.search(r'\babc\b','bc abc abc')
print(result.group()) # abc

四、\B:
作用:不是匹配單詞開始或結束的位置,和\b是相反的。
比如:\Ba它表示匹配不以a開始的單詞,所以可以匹配bac,cba但是不能匹配abc

result = re.search(r'\Ba','bac')
print(result.group()) # a
result = re.search(r'\Ba','abc')
print(result) # None

4.一般字符

一、.:
作用:匹配除換行符之外的任何單個字符。
比如:ab.可以匹配abc,abd,abe等等

result = re.search(r'Co.e.d','CodeId')
print(result.group()) # CodeId

二、\:
作用:轉義字符,改變后面一個字符原本的字符意思。
比如:n原本匹配字符n,但是在前面加上\之后就變成\n,用來匹配換行符。

result = re.search(r'Co\n.','Co\ndeId')
print(result.group())
'''
Co
d
'''

三、[]:
作用:字符集合。匹配集合中所包含的任意一個字符。其中集合中的元素可以一一列出,也可以寫范圍。
比如:[abco]可以匹配CodeId中的o[0-9]等同于[0123456789]

result = re.search(r'[0-9]','a1b')
print(result.group()) # 1
result = re.search(r'[oI]','CodeId')
print(result.group()) # o

注意:如果[]里面的第一個字符是^,那么表示取反的意思。比如:[^0-9]表示匹配不是數字的字符。

result = re.search(r'[^0-9]','a1b')
print(result.group()) # a

四、|:
作用:或的意思
比如:x|y表示先匹配x表達式如果不成功就匹配y表達式。

result = re.search(r'ab|ac','abc')
print(result.group()) # ab

5.分組

分組不是對數據進行分組,而是對匹配的表達式進行分組。看一下下面的講解應該會明白一些。
一、(...):
作用:可以匹配括號中的任何表達式,同時也標志著組的開始和結束。當表達式中有多個括號時,從左向右,第一個左括號為第一組,第二個左括號為第二組,以此類推。
比如:(a){2}(b){3}會匹配aabbb,其中a是第一組,b是第二組

result = re.search(r'(a){2}(b){3}(c*)','aabbb')
print(result.group()) # aabbb
print(result.groups()) # ('a', 'b', '')

注意:result.groups()的作用是返回所有匹配的子組的元組,比如上面a,b都匹配上了,而c沒有匹配上所以返回c組為空
二、(?P<name>...):
作用:在分組的同時,為組起一個名稱,這個組名稱必須是有效的Python標識符,并且每個組名稱只能在正則表達式中定義一次。
比如:(?P<A>a)就是為組起了一個名稱A.

result = re.search(r'(?P<A>a){2}(b){3}(a*)','aabbb')
# 通過組名稱來組的匹配內容
print(result.group('A')) # a

三、(?P=name):
作用:引用表達式前面組中名稱為name的組的匹配內容。
比如:(?P<A>.){2}(b){3}(?P=A)匹配的字符可以是aabbbaccbbbc,ddbbbd….

result = re.search(r'(?P<A>.){2}(b){3}(?P=A)','aabbba')
print(result.group()) # aabbba

四、\number:
作用:引用表達式中編號為number的組的匹配內容。
比如:([0-9])([a-z])\1匹配的字符串有1a1,2s2,6a6

result = re.search(r'([0-9])([a-z])\1','6a6')
print(result.group())# 6a6

6.反向引用

反向引用涉及到組(被圓括號括起來的部分),組在匹配到內容時,會存儲到緩沖區,按照存儲的先后順序,分別編號為1,2,3…99,最高到99。每個緩沖區的內容可以使用\number的方式進行訪問調用。

7.非獲取匹配

非獲取匹配:就是組中匹配的內容不進行緩存,不供以后使用
一、(?:...):
作用:可以匹配括號中的任何表達式,但是不進行緩存以供后面使用。
比如:(?:123)abc\1表達式會報錯,因為前面的組沒有進行緩存,\1調用時會失敗。
二、(?=...):
作用:起到一個條件約束的功能,約束括號前面的字符串。看做如果是...
比如:ab(?=c)會匹配abc中的ab但是不會匹配abd中的ab。換一種說法就是:如果ab的后面是c就匹配成功,否則失敗。

result = re.search(r'ab(?=c)','abc')
print(result.group()) # ab
result = re.search(r'ab(?=c)','abd')
print(result) # None

三、(?!...):
作用:起到一個條件約束的功能,約束括號前面的字符串。看做如果不是...
比如:ab(?!c)會匹配abd中的ab但是不會匹配abc中的ab。換一種說法就是:如果ab的后面不是c就匹配成功,否則失敗。

result = re.search(r'ab(?!c)','abc')
print(result) # None
result = re.search(r'ab(?!c)','abd')
print(result.group()) # ab

四、(?<=...):
作用:起到一個條件約束的功能,約束括號后面的字符串。看做如果前面是...
比如:(?<=c)ab會匹配cab中的ab,但是不會匹配dab中的ab。換一種說法就是:如果ab的前面是c就匹配成功,否則失敗。

result = re.search(r'(?<=c)ab','cab')
print(result.group()) # ab
result = re.search(r'(?<=c)ab','dab')
print(result) # None

五、(?<!...):
作用:起到一個條件約束的功能,約束括號后面的字符串。看做如果前面不是...
比如:(?<!c)ab會匹配dab中的ab但是不會匹配cab中的ab。換一種說法就是:如果ab的前面不是c就匹配成功,否則失敗。

result = re.search(r'(?<!c)ab','cab')
print(result) # None
result = re.search(r'(?<!c)ab','dab')
print(result.group()) # ab

8.表達式的注釋

注釋在表達式中起到解釋說明的作用。
一、(?#...):
作用:起到注釋作用,括號中的字符在表達式中運行時,不啟動用。
比如:a(?#letter)只會匹配單個字符a,而letter是解釋說明a是一個字母,方便閱讀。

result = re.search(r'a(?#letter)','cab')
print(result.group()) # a

9.預定義

就是提前設定好一些字符代表什么意思,用來替換一些復雜的字符。
一、\d\D:
代表:一個表示[0-9],另一個表示[^0-9],它倆是對立的。
作用:\d表示匹配0-9中任意一個數字。\D表示匹配非數字的字符。
比如:a\d可以匹配a1,a0,a2,a6…;而a\D表示匹配aa,ab,a;只要a后面不是數字就行。

result = re.search(r'a\d','a1')
print(result.group()) # a1
result = re.search(r'a\D','a1')
print(result) # None

二、\w\W:
代表:一個表示'[A-Za-z0-9_],另一個表示'[^A-Za-z0-9_],它倆是對立的。
作用:\w表示匹配字母、數字、下劃線;\W表示匹配非字母數字下劃線。
比如:\w+匹配13,時會得到13,而\W+匹配時只會匹配到

result = re.search(r'\w+','13,')
print(result.group()) # 13
result = re.search(r'\W+','13,')
print(result.group()) # ,

三、\s\S:
代表:一個表示[ \f\n\r\t\v],另一個表示[^ \f\n\r\t\v];
作用:\s表示匹配任何空白字符,包括空格、制表符、換頁符等等,而\S表示匹配任何非空白字符。
比如:a\sc可以匹配a c,而a\Sc卻不能。

result = re.search(r'a\sc','a c')
print(result.group()) # a c
result = re.search(r'a\Sc','a c')
print(result) # None

四、\A\Z:
作用:\A表示匹配字符串的開頭,\Z表示匹配字符串的結尾。
比如:\Aa會匹配字符串abcdcba中,開始的a,a\Z會匹配字符串abcdcba中結尾處的a

result = re.search(r'\Aa','abcdcba')
print(result) # <_sre.SRE_Match object; span=(0, 1), match='a'>
result = re.search(r'a\Z','abcdcba')
print(result) # <_sre.SRE_Match object; span=(6, 7), match='a'>

今天的學習暫時告一段落,后面會不定時更新的。送大家一句話人必須相信自己,這是成功的秘訣
下面是我的公眾號:CodeId 歡迎關注

公眾號:CodeId
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容