元字符(Meta Characters)是正則表達(dá)式中具有特殊意義的專用字符,Python中是用來指明前導(dǎo)字符(位于元字符前的字符)在目標(biāo)對象中的出現(xiàn)模式。 元字符是正則表達(dá)式最核心和基本的概念 整套學(xué)習(xí)自學(xué)教程中應(yīng)用的數(shù)據(jù)都是《三國志》、《真·三國無雙》系列游戲中的內(nèi)容。 正則表達(dá)式元字符在正則表達(dá)式中,方括號(hào) ( [] ) 中指定的一組字符組成一個(gè)字符類。 元字符序列匹配類中的任何單個(gè)字符。 s = 'Dynasty123Dynasty'# 3個(gè)任意連續(xù)字符匹配re.search('[0-9][0-9][0-9]', s)<_sre.SRE_Match object; span=(7, 10), match='123'>re.search('[0-9][0-9][0-9]', 'Dynasty456Dynasty')<_sre.SRE_Match object; span=(7, 10), match='456'>re.search('[0-9][0-9][0-9]', '234baz')<_sre.SRE_Match object; span=(0, 3), match='234'>re.search('[0-9][0-9][0-9]', 'qux678')<_sre.SRE_Match object; span=(3, 6), match='678'># 匹配不上的情況print(re.search('[0-9][0-9][0-9]', '12Dynasty34'))None 通配符點(diǎn) ( . ) 元字符匹配除換行符以外的任何字符。
re模塊支持的元字符下面列表都是元字符的描述,對元字符進(jìn)行分類描述方便記憶。 這個(gè)要是看不懂直接跳過看下面的例子。
類別1:匹配單個(gè)字符的元字符方括號(hào)( [] ) 字符集 指定要匹配的特定字符集。 字符類元字符序列將匹配該類中包含的任何單個(gè)字符。 # 元字符序列[nasty]匹配任何單個(gè)'n'、'a'、's'、't'或'y'字符re.search('Dy[nasty]', 'DynastyDynastyzz')<_sre.SRE_Match object; span=(0, 3), match='Dyn'> 匹配和[a-z]之間的任何小寫字母字符。
匹配和[0-9]之間任何數(shù)字字符。 re.search('[0-9][0-9]', 'Dynasty123Dynasty')<_sre.SRE_Match object; span=(7, 9), match='12'> [0-9a-fA-F]匹配任何十六進(jìn)制數(shù)字字符。
[^0-9]匹配任何不是數(shù)字的字符開頭的字符。 re.search('[^0-9]', '12345Dynasty')<_sre.SRE_Match object; span=(5, 6), match='D'> 如果一個(gè)^字符出現(xiàn)在字符類中但不是第一個(gè)字符則無結(jié)果。
可以通過用連字符分隔字符來指定字符類中的字符范圍,可以將其作為第一個(gè)或最后一個(gè)字符放置,或者使用反斜杠 ( \ ) 對其進(jìn)行轉(zhuǎn)義。 # 直接查找符號(hào)re.search('[-abc]', '123-456')<_sre.SRE_Match object; span=(3, 4), match='-'>re.search('[abc-]', '123-456')<_sre.SRE_Match object; span=(3, 4), match='-'>re.search('[ab\-c]', '123-456')<_sre.SRE_Match object; span=(3, 4), match='-'># 查找轉(zhuǎn)義符號(hào)re.search('[]]', 'Dynasty[1]')<_sre.SRE_Match object; span=(9, 10), match=']'>re.search('[ab\]cd]', 'Dynasty[1]')<_sre.SRE_Match object; span=(3, 4), match='a'># [ ] 內(nèi)的元字符失去意義轉(zhuǎn)義成字符處理re.search('[)*+|]', '123*456')<_sre.SRE_Match object; span=(3, 4), match='*'>re.search('[)*+|]', '123+456')<_sre.SRE_Match object; span=(3, 4), match='+'> 點(diǎn) ( . ) 通配符 匹配除換行符以外的任何單個(gè)字符。
\w 和 \W 單詞字符匹配 \w匹配任何字母數(shù)字字符,單詞字符是大寫和小寫字母、數(shù)字和下劃線 ( _) 字符。 \w 等于 [a-zA-Z0-9_] 。 re.search('\w', '#(.a$@&')<_sre.SRE_Match object; span=(3, 4), match='a'>re.search('[a-zA-Z0-9_]', '#(.a$@&')<_sre.SRE_Match object; span=(3, 4), match='a'> \W是相反的。它匹配任何非單詞字符。 \W 等于 [^a-zA-Z0-9_] 。
\d 和 \D 字符十進(jìn)制數(shù)字匹配 \d匹配任何十進(jìn)制數(shù)字字符,等價(jià)于[0-9]。 re.search('\d', 'abc4def')<_sre.SRE_Match object; span=(3, 4), match='4'> \D匹配任何不是十進(jìn)制數(shù)字的字符,等價(jià)于[^0-9]。
\s 和 \S 字符空格匹配 \s匹配任何空白字符,同時(shí)也匹配換行符。 re.search('\s', 'Dynasty\nDynasty')<_sre.SRE_Match object; span=(3, 4), match='\n'> \S匹配任何不是空格的字符。
混合使用 \w, \W, \d, \D, \s, 和\S 字符類序列\(zhòng)w, \W, \d, \D, \s, 和\S也可以出現(xiàn)在方括號(hào)字符類中。 # [\d\w\s]匹配任何數(shù)字、單詞或空白字符re.search('[\d\w\s]', '---3---')<_sre.SRE_Match object; span=(3, 4), match='3'>re.search('[\d\w\s]', '---a---') <_sre.SRE_Match object; span=(3, 4), match='a'>re.search('[\d\w\s]', '--- ---')<_sre.SRE_Match object; span=(3, 4), match=' '># 由于\w包含\d,相同的字符類也可以表示為略短[\w\s]re.search('[\w\s]', '---a---')<_sre.SRE_Match object; span=(3, 4), match='a'>re.search('[\w\s]', '--- ---')<_sre.SRE_Match object; span=(3, 4), match=' '> 類別2:轉(zhuǎn)義元字符反斜杠 ( \ ) 轉(zhuǎn)義元字符 反斜杠會(huì)刪除元字符的特殊含義。
類別3:錨點(diǎn)不匹配搜索字符串中的任何實(shí)際字符,并且在解析期間它們不使用任何搜索字符串。指示搜索字符串中必須發(fā)生匹配的特定位置。 ^ 和 \A 字符串的開頭匹配項(xiàng) re.search('^Dynasty', 'DynastyDynasty')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>re.search('\ADynasty', 'DynastyDynasty')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'> $ 和\Z 字符串的結(jié)尾匹配項(xiàng)
\b 和 \B 單詞匹配 \b 必須在單詞的開頭或結(jié)尾。 # 單詞開頭re.search(r'\bDynasty', 'Dynasty Dynasty')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>re.search(r'\bDynasty', 'Dynasty.Dynasty')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>print(re.search(r'\bDynasty', 'DynastyDynasty'))<_sre.SRE_Match object; span=(0, 7), match='Dynasty'># 單詞結(jié)尾re.search(r'Dynasty\b', 'Dynasty Dynasty')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>re.search(r'Dynasty\b', 'Dynasty.Dynasty')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>print(re.search(r'Dynasty\b', 'DynastyDynasty'))<_sre.SRE_Match object; span=(7, 14), match='Dynasty'># 單詞居中re.search(r'\bDynasty\b', 'Dynasty Dynasty ba')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>re.search(r'\bDynasty\b', 'Dynasty(Dynasty)ba')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>print(re.search(r'\bDynasty\b', 'DynastyDynastyba'))None \B 不能在單詞的開頭或結(jié)尾。
類別4:量詞該部分必須出現(xiàn)多少次才能使匹配成功。 * 匹配前面的子表達(dá)式零次或多次 re.search('Dynasty-*Dynasty', 'DynastyDynasty') <_sre.SRE_Match object; span=(0, 14), match='DynastyDynasty'>re.search('Dynasty-*Dynasty', 'Dynasty-Dynasty') <_sre.SRE_Match object; span=(0, 15), match='Dynasty-Dynasty'>re.search('Dynasty-*Dynasty', 'Dynasty--Dynasty') <_sre.SRE_Match object; span=(0, 16), match='Dynasty--Dynasty'> 匹配2個(gè)字符中全部的內(nèi)容。
+ 匹配前面的子表達(dá)式一次或多次 print(re.search('Dynasty-+Dynasty', 'DynastyDynasty')) Nonere.search('Dynasty-+Dynasty', 'Dynasty-Dynasty') <_sre.SRE_Match object; span=(0, 15), match='Dynasty-Dynasty'>re.search('Dynasty-+Dynasty', 'Dynasty--Dynasty') <_sre.SRE_Match object; span=(0, 16), match='Dynasty--Dynasty'> ? 匹配前面的子表達(dá)式零次或一次
.*?、+?、?? 最小長度匹配 + 和 +? 代替了 * 和 *?,加問號(hào)則表示為最小長度匹配的懶惰模式。 # .*全匹配貪婪模式re.search('<.*>', '%<Dynasty> <Dynasty> <zs>%')<_sre.SRE_Match object; span=(1, 25), match='<Dynasty> <Dynasty> <sz>'># *? 前一個(gè)字符0次或無限次擴(kuò)展,最小匹配re.search('<.*?>', '%<Dynasty> <Dynasty> <sz>%')<_sre.SRE_Match object; span=(1, 10), match='<Dynasty>'># .+ 前一個(gè)字符1次或無限次擴(kuò)展,最小匹配re.search('<.+>', '%<Dynasty> <Dynasty> <zs>%')<_sre.SRE_Match object; span=(1, 25), match='<Dynasty> <Dynasty> <zs>'># .+? 前一個(gè)字符1次或無限次擴(kuò)展,最小匹配re.search('<.+?>', '%<Dynasty> <Dynasty> <zs>%')<_sre.SRE_Match object; span=(1, 10), match='<Dynasty>'># ? 匹配懶惰模式re.search('ba?', 'baaaa')<_sre.SRE_Match object; span=(0, 2), match='ba'># ?? 前一個(gè)字符0次或1次擴(kuò)展,最小匹配re.search('ba??', 'baaaa')<_sre.SRE_Match object; span=(0, 1), match='b'> {m} 完全匹配m次前面元字符的正則表達(dá)式。
{m,n} 匹配前面正則表達(dá)式的任意數(shù)量的重復(fù)從m到n次。 for i in range(1, 6): s = f'x{'-' * i}x' print(f'{i} {s:10}', re.search('x-{2,4}x', s))1 x-x None2 x--x <_sre.SRE_Match object; span=(0, 4), match='x--x'>3 x---x <_sre.SRE_Match object; span=(0, 5), match='x---x'>4 x----x <_sre.SRE_Match object; span=(0, 6), match='x----x'>5 x-----x None
{m,n}? 只匹配一次。 非貪婪(懶惰)版本 {m,n}。 re.search('a{3,5}', 'aaaaaaaa')<_sre.SRE_Match object; span=(0, 5), match='aaaaa'>re.search('a{3,5}?', 'aaaaaaaa')<_sre.SRE_Match object; span=(0, 3), match='aaa'> 類別5:分組構(gòu)造和反向引用分組構(gòu)造將 Python 中的正則表達(dá)式分解為子表達(dá)式或組。 (<regex>),定義子表達(dá)式或組。 括號(hào)中的正則表達(dá)式僅匹配括號(hào)的內(nèi)容。
將組視為一個(gè)單元 組后面的量詞元字符對組中指定的整個(gè)子表達(dá)式作為一個(gè)單元進(jìn)行操作。 re.search('Dynasty+', 'Dynasty Dynasty zs')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>re.search('(Dynasty)+', 'Dynasty Dynasty zs')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>re.search('(Dynasty)+', 'Dynasty DynastyDynasty zs')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'>
捕獲組,m.groups() 返回一個(gè)元組,其中包含從正則表達(dá)式匹配中捕獲的所有組。
捕獲組,m.group(<n>) 返回包含<n>捕獲的匹配項(xiàng)的字符串。 m = re.search('(\w+),(\w+),(\w+)', 'Dynasty,qw,ba')m.groups()('Dynasty', 'qw', 'ba')m.group(0)'Dynasty,qw,ba'm.group(1)'Dynasty'm.group(2)'qw'm.group(3)'ba' 捕獲組,m.group(<n1>, <n2>, ...) 返回一個(gè)包含指定捕獲匹配序號(hào)的元組。
類別6:反向引用\<num> 匹配連續(xù)相同字符 regex = r'(\w+),\1'm = re.search(regex, 'Dynasty,Dynasty')m<_sre.SRE_Match object; span=(0, 15), match='Dynasty,Dynasty'>m.group(1)'Dynasty' 類別7:其他分組結(jié)構(gòu)(?P<name><regex>) 創(chuàng)建捕獲組并命名。
(?P=<name>) 匹配先前捕獲名的內(nèi)容。 m = re.search(r'(\w+),\1', 'Dynasty,Dynasty')m<_sre.SRE_Match object; span=(0, 15), match='Dynasty,Dynasty'>m.group(1)'Dynasty'm = re.search(r'(?P<word>\w+),(?P=word)', 'Dynasty,Dynasty')m<_sre.SRE_Match object; span=(0, 15), match='Dynasty,Dynasty'>m.group('word')'Dynasty' (?:<regex>) 創(chuàng)建一個(gè)非捕獲組。
類別8:Lookahead 和 Lookbehind 斷言根據(jù)解析器在搜索字符串中當(dāng)前位置的后面(左側(cè))或前面(右側(cè))來確定 Python 中正則表達(dá)式匹配的成功或失敗。 (?=<lookahead_regex>) 積極前瞻斷言。 斷言正則表達(dá)式解析器當(dāng)前位置之后的內(nèi)容必須匹配。 # 前瞻斷言(?=[a-z])指定后面的'Dynasty'必須是小寫字母字符。re.search('Dynasty(?=[a-z])', 'Dynastydynasty')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'># 前瞻失敗的例子,Dynasty的下一個(gè)字符是'1'print(re.search('Dynasty(?=[a-z])', 'Dynasty123'))None# 前瞻的獨(dú)特之處<lookahead_regex>在于不消耗搜索字符串中匹配的部分,并且它不是返回的匹配對象的一部分。re.search('Dynasty(?=[a-z])', 'Dynastydynasty')<_sre.SRE_Match object; span=(0, 7), match='Dynasty'># 舉例對比觀察,?=斷言的區(qū)別m = re.search('Dynasty(?=[a-z])(?P<ch>.)', 'Dynastydynasty')m.group('ch')'d'm = re.search('Dynasty([a-z])(?P<ch>.)', 'Dynastydynasty')m.group('ch')'y' (?!<lookahead_regex>) 否定的前瞻斷言。
(?<=<lookbehind_regex>) 積極的后向斷言。 斷言正則表達(dá)式解析器當(dāng)前位置之前的內(nèi)容匹配。 # 斷言指定'Dynasty'必須先于'Dynasty're.search('(?<=Dynasty)Dynasty', 'DynastyDynasty')<_sre.SRE_Match object; span=(7, 14), match='Dynasty'>print(re.search('(?<=qux)Dynasty', 'DynastyDynasty'))None (?<!--<lookbehind_regex-->) 否定的向后斷言。
類別9:雜項(xiàng)元字符(?#...) 指定注釋。 正則表達(dá)式解析器忽略(?#...)序列中包含的任何內(nèi)容 re.search('Dynasty(?#xxxx xxxx) *ba', 'Dynasty Dynasty ba qw')<_sre.SRE_Match object; span=(8, 18), match='Dynasty ba'> 豎條或管道 ( | ) 指定要匹配的一組備選方案。 形式的表達(dá)式最多匹配一個(gè)指定的表達(dá)式:<regex1>|<regex2>|...|<regexn><regexi>
結(jié)合交替、分組和任何其他元字符來實(shí)現(xiàn)需要的任何復(fù)雜程度。 # (Dynasty|Dynasty|ba)+表示一個(gè)或多個(gè)字符串re.search('(Dynasty|Dynasty|ba)+', 'DynastyDynastyDynasty')<_sre.SRE_Match object; span=(0, 21), match='DynastyDynastyDynasty'>re.search('(Dynasty|Dynasty|ba)+', 'bazbazbazbaz')<_sre.SRE_Match object; span=(0, 2), match='ba'>re.search('(Dynasty|Dynasty|ba)+', 'DynastybazDynasty')<_sre.SRE_Match object; span=(0, 9), match='Dynastyba'> |
|