【自然語言處理基礎技能(NLP)】python正則表達式

正則表達式規則表:

正則表達式測試連接 :http://regexr.com/

進階練習:https://alf.nu/RegexGolf

python 【re模塊】

 

s = 'ABC\\-001' # Python的字符串
# 對應的正則表達式字符串變成:
# 'ABC\-001'
#建議使用Python的r前綴,就不用考慮轉義的問題了:

s = r'ABC\-001' # Python的字符串
# 對應的正則表達式字符串不變:
# 'ABC\-001'
#先看看如何判斷正則表達式是否匹配:

>>> import re
>>> re.match(r'^\d{3}\-\d{3,8}$', '010-12345')
<_sre.SRE_Match object; span=(0, 9), match='010-12345'>
>>> re.match(r'^\d{3}\-\d{3,8}$', '010 12345')
>>>
# match()方法判斷是否匹配,如果匹配成功,返回一個Match對象,否則返回None。常見的判斷方法就是:

test = '用戶輸入的字符串'
if re.match(r'正則表達式', test):
    print('ok')
else:
    print('failed')
import re
#^d{3}表示前三位爲三個數字,^表示的是指前三位,超過三位會報錯
m=re.match(r'^\d{3}-\d{3,8}$', '111-123456')
print(m.string)
#用正則表達式切分字符串比用固定的字符更靈活,請看正常的切分代碼:
print('a b   c'.split(' '))

#無法識別連續的空格,用正則表達式試試:
print(re.split(r'\s+', 'a b   c'))
print(re.split(r'\S+', 'a b   c'))

#無論多少個空格都可以正常分割。加入,試試:

print(re.split(r'[\s\,]+', 'a,b, c  d'))

#再加入;試試:

print(re.split(r'[\s\,\;]+', 'a,b;; c  d'))

#除了簡單地判斷是否匹配之外,正則表達式還有提取子串的強大功能。用()表示的就是要提取的分組(Group)。比如:

#^(\d{3})-(\d{3,8})$分別定義了兩個組,可以直接從匹配的字符串中提取出區號和本地號碼:

m1 = re.match(r'^(\d{3})-(\d{3,8})$', '010-12345')

print(m1.group(0))
print(m1.group(1))
print(m1.group(2))

t='09:09:09'
#以下寫法識別時間錯誤,不能真缺識別非時間字符串
m=re.match(r'^([0-9][0-9])\:([0-9][0-9])\:([0-9][0-9])',t)
print(m.groups())
#以下爲識別時間的正確寫法:
# | 優先匹配左側的表達式,一旦左側的表達式匹配成功,則忽略右側的其它表達式匹配
m2 = re.match(r'^(0[0-9]|1[0-9]|2[0-3]|[0-9])\:(0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]|[0-9])'
              r'\:(0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]|[0-9])$', t)
print(m2.groups())

#正則匹配是貪婪匹配,會儘可能多的匹配
print(re.match(r'^(\d+)(0*)$', '102300').groups())

#貪婪匹配
#最後需要特別指出的是,正則匹配默認是貪婪匹配,也就是匹配儘可能多的字符。舉例如下,匹配出數字後面的0:

print(re.match(r'^(\d+)(0*)$', '102300').groups())

#由於\d+採用貪婪匹配,直接把後面的0全部匹配了,結果0*只能匹配空字符串了。
#必須讓\d+採用非貪婪匹配(也就是儘可能少匹配),才能把後面的0匹配出來,加個?就可以讓\d+採用非貪婪匹配:
#注意:這裏不能省去d後面的+號,不然會報錯
print( re.match(r'^(\d+?)(0*)$', '102300').groups())

#重複利用同一正則表達式時,節省時間方法:一次編譯,多次使用。
#當我們在Python中使用正則表達式時,re模塊內部會幹兩件事情:編譯正則表達式,如果正則表達式的字符串本身不合法,會報錯;
#用編譯後的正則表達式去匹配字符串。如果一個正則表達式要重複使用幾千次,出於效率的考慮,我們可以預編譯該正則表達式,接
# 下來重複使用時就不需要編譯這個步驟了,直接匹配:

import re
# 編譯:
re_telephone = re.compile(r'^(\d{3})-(\d{3,8})$')
# 使用:
print(re_telephone.match('010-12345').groups()) 
print(re_telephone.match('010-8086').groups())

結果顯示:

 

 

 

使用re的一般步驟是

  • 1.將正則表達式的字符串形式編譯爲Pattern實例
  • 2.使用Pattern實例處理文本並獲得匹配結果(一個Match實例)
  • 3.使用Match實例獲得信息,進行其他的操作。
# encoding: UTF-8
import re
 
# 將正則表達式編譯成Pattern對象
pattern = re.compile(r'hello.*\!')
 
# 使用Pattern匹配文本,獲得匹配結果,無法匹配時將返回None
match = pattern.match('hello, hanxiaoyang! How are you?')
 
if match:
    # 使用Match獲得分組信息
    print match.group()
hello, hanxiaoyang!

 

re.compile(strPattern[, flag]):

  • re.I(re.IGNORECASE): 忽略大小寫(括號內是完整寫法,下同)
  • re.M(MULTILINE): 多行模式,改變'^'和'$'的行爲(參見上圖)
  • re.S(DOTALL): 點任意匹配模式,改變'.'的行爲
  • re.L(LOCALE): 使預定字符類 \w \W \b \B \s \S 取決於當前區域設定
  • re.U(UNICODE): 使預定字符類 \w \W \b \B \s \S \d \D 取決於unicode定義的字符屬性
  • re.X(VERBOSE): 詳細模式。這個模式下正則表達式可以是多行,忽略空白字符,並可以加入註釋。以下兩個正則表達式是等價的:
regex_1 = re.compile(r"""\d +  # 數字部分
                         \.    # 小數點部分
                         \d *  # 小數的數字部分""", re.X)
regex_2 = re.compile(r"\d+\.\d*")

 

 

 

 

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章