python day15
?
昨日內容補充:
?
對于兩個文件中的互相導入md模塊問題分析:
x = 1from md import xprint(x)# md中的xfrom md import xx = 1000print(x)# 當前文件中的x__all__ 列表寫什么,執(zhí)行導入語句那個文件就能拿到什么;
__all__不寫的情況,默認是將所在文件所有的名字都暴露給導入者.
解決循環(huán)導入的第三種方式(前兩種已在day14涉及):
- 將循環(huán)導入的名字,放到另外一個文件中
?
正則表達式
定義:?正則就是用來篩選字符串中的特定的內容的,對字符串進行操作的邏輯工具
re模塊與正則表達式之間的關系:
- 正則表達式不是python獨有的,它是一門獨立技術
- 所有的編程語言都可以用正則
- 如果想在python中用,就必須依賴于re模塊
相關書籍:?<正則指引>
驗證工具: www.tool.chinaz.com
正則的應用場景:
- 1.爬蟲
- 2.數據分析
?注意點:?只要是reg...一般情況下都是跟正則有關,而且如果想匹配具體的內容,可以直接寫完整的內容,不需要寫正則
?
字符組[ ]:
| 正則 | 待匹配字符 ? | ?匹配結果 | 說明 |
| ? [0123456789] | ?8 | ? True | 在一個字符組里枚舉合法的所有字符,字符組里的任意一個字符 和"待匹配字符"相同都視為可以匹配 |
| ? [0123456789] | ?a | ? False | ? 由于字符組中沒有"a"字符,所以不能匹配 |
| ? [0-9] | ?7 | ? True | ? 也可以用-表示范圍,[0-9]就和[0123456789]是一個意思 |
| ? [a-z] | ?s | ? True | ? 同樣的如果要匹配所有的小寫字母,直接用[a-z]就可以表示 |
| ? [A-Z] | ?B | ? True | ? [A-Z]就表示所有的大寫字母 |
| ? [0-9a-fA-F] | ?e | ? True | ? 可以匹配數字,大小寫形式的a~f,用來驗證十六進制字符 |
關于字符:
| 元字符 | 匹配內容 |
| . | 匹配除換行符以外的任意字符 |
| \w | 匹配字母或數字或下劃線 |
| \s | 匹配任意的空白符 |
| \d | 匹配數字 |
| \n | 匹配一個換行符 |
| \t | 匹配一個制表符 |
| \b | 匹配一個單詞的結尾 |
| ^ | 匹配字符串的開始 |
| $ | 匹配字符串的結尾 |
| \W | 匹配非字母或數字或下劃線 |
| \D | 匹配非數字 |
| \S | 匹配非空白符 |
| a|b | 匹配字符a或字符b |
| () | 匹配括號內的表達式,也表示一個組 |
| [...] | 匹配字符組中的字符 |
| [^...] | 匹配除了字符組中字符的所有字符 |
?
關于量詞:
| 量詞 | 用法說明 |
| * | 重復零次或更多次 |
| + | 重復一次或更多次 |
| ? | 重復零次或一次 |
| {n} | 重復n次 |
| {n,} | 重復n次或更多次 |
| {n,m} | 重復n到m次 |
注意點:
- 通常一個字符組里面的表達式都是或關系
- \w:\word與\W相反
- \s:\space與\S相反
- \d:\digit與\D相反
- ^匹配字符串的開始 類似于startswith
- $匹配字符串的結尾 類似于endswith
- ^如果直接寫在外面,就是限制字符串開頭的作用
- [^...]就是取反的意思,除了...之外其他都能輸出
- a|b,如果是abc|ab,一定要將長的放在前面
PS: ^與$連用,就能精準限制匹配的內容,兩者之間寫什么,匹配的字符串就必須是什么,多一個不行,少一個也不行
例如:^jason$,最終輸出結果就一定是jason
貪婪匹配Patten與非貪婪匹配:
| 正則 | 待匹配字符 | 匹配結果 | 說明 |
| <.*> | <script>...<script> | <script>...<script> | 默認為貪婪匹配模式,會匹配盡量長的字符串 |
| <.*?> | r'\d' | ? ?<script> <script> | 加上?為將貪婪匹配模式轉為非貪婪匹配模式,會匹配盡量短的字符串 |
-
<.*>:先拿著里面的.*去匹配所有的內容,然后再根據>往回退著找,遇到即停止
-
<.*?>:先拿著?后面的>去匹配符合條件的最少的內容,然后把匹配的結果返回
PS:根據匹配的內部原理可以很好的理解,?.*?x?就是取前面任意長度的字符,直到一個x出現(xiàn)
?
注意點:
- 正則在匹配的時候默認都是貪婪匹配(盡量匹配多的)
- 量詞必須跟在正則符號后面
- 量詞只能夠限制緊挨著它的左側表達式的那一個正則符號
- 量詞后面加上一個?就可以將貪婪匹配變成非貪婪匹配(惰性匹配)
分組() 或| [^]:
| 正則 | 待匹配字符 | 匹配結果 | 說明 |
| ^[1-9]\d{13,16}[0-9x]$ | 110101198001017032 | 110101198001017032 | 表示可以匹配一個正確的身份證號 |
| ^[1-9]\d{13,16}[0-9x]$ | 1101011980010170 | 1101011980010170 | 表示也可以匹配這串數字,但這并不是一個正確的身份證號碼,它是一個16位的數字 |
| ^[1-9]\d{14}(\d{2}[0-9x])?$ | 1101011980010170 | False | 現(xiàn)在不會匹配錯誤的身份證號了 ()表示分組,將\d{2}[0-9x]分成一組,就可以整體約束他們出現(xiàn)的次數為0-1次 |
| ^([1-9]\d{16}[0-9x]|[1-9]\d{14})$ | 110105199812067023 | 110105199812067023 | 表示先匹配[1-9]\d{16}[0-9x]如果沒有匹配上就匹配[1-9]\d{14} |
定義:當多個正則符號需要重復多次時,或者當作一個整體進行其他操作,那么可以分組
分組在正則的語法中就是( )
例如:?用[a-z][0-9]會匹配到三個結果,這個時候就可以用分組([a-z][0-9])+,可以提高不少效率
例題:?關于身份證的正則表達式
- ^[1-9]\d{14}(\d{2}[0-9x])?$
- ^([1-9]\d{16}[0-9x]|[1-9]\d{14})$
?上面三種都是解決方法,第三種考慮的最全面
轉義符:
| 正則 | 待匹配字符 | 匹配結果 | 說明 |
| ?\n | ?\n | ?False | 因為在正則表達式中\(zhòng)是有特殊意義的字符,所以要匹配\n本身,用表達式\n無法匹配 |
| \\n? | \n? | ??True | ? 轉義\之后變成\\,即可匹配 |
| ?'\\\\n' | ?'\\n' | ??True | ? 如果在python中,字符串中的'\'也需要轉義,所以每一個字符串'\'又需要轉義一次 |
| ?r'\\n' | ?r'\n' | ??True | ? 在字符串之前加r,讓整個字符串不轉義 |
注意點:
- 在正則表達式中,有很多有特殊意義的是元字符,比如\n和\s等,如果要在正則中匹配正常的"\n"而不是"換行符"就需要對""進行轉義,變成'\'
- python中,無論是正則表達式,還是待匹配的內容,都是以字符串的形式出現(xiàn)的
- 字符串中\也有特殊的含義,本身還需要轉義
- 如果匹配一次"\n",字符串中要寫成'\\n'
- 如果匹配一次"\\n",字符串中要寫成'\\\\n'
- r'\\n' 在字符串前面加個r,讓整個字符串不轉義(了解:r其實就是real的意思,真實不轉義)
?
re模塊:
?
定義:python中使用正則必須借助于re模塊,或者是支持正則表達式書寫的功能與方法
while True:phone_number = input('please input your phone number : ')if len(phone_number) == 11 \and phone_number.isdigit()\and (phone_number.startswith('13') \or phone_number.startswith('14') \or phone_number.startswith('15') \or phone_number.startswith('16') \or phone_number.startswith('17') \or phone_number.startswith('18')):print('是合法的手機號碼')else:print('不是合法的手機號碼')import rephone_number = input('please input your phone number : ')if re.match('^(13|14|15|16|17|18)[0-9]{9}$',phone_number):print('是合法的手機號碼')else:print('不是合法的手機號碼') 運用正則表達式+re模塊來解決用戶以手機號來注冊并驗證的問題三種主要方法:
- findall:?找出字符串中符合正則表達式的全部內容,并且返回的是一個列表,列表中的元素就是正則匹配到的結果
- searfch:?只會依據正則查一次 只要查到了結果,就不會再往后查找;當查找的結果不存在的情況下 調用group直接報錯
- match:?只會匹配字符串的開頭部分;當字符串的開頭不符合匹配規(guī)則的情況下 返回的也是None 調用group也會報錯
其他方法:
split:分割
ret = re.split('[ab], 'abcd') # 先按'a'分割得到' '和'bcd',再對' '和'bcd'分別按'b'分割print(ret) # 返回的還是列表[' ', ' ', 'cd'] splitsub:替換,先按照正則表達式查找所有符合該表達式的內容 統(tǒng)一替換成'新的內容' 還可以通過n來控制替換的個數
ret = re.sub('\d', 'H','eva3egon4yuan4',1) # 將數字替換成'H',參數1表示只替換1個# sub('正則表達式', '新的內容', '待替換的字符串',n)print(ret) # 返回值為evaHegon4yuan4 subsubn:替換(返回元祖)
ret = re.subn('\d', 'H', 'eva3egon4yuan4') # 將數字替換成'H',返回元組(替換的結果,替換了多少次) ret1 = re.subn('\d', 'H', 'eva3egon4yuan4',1) # 將數字替換成'H',返回元組(替換的結果,替換了多少次)print(ret) # 返回的是一個元組 元組的第二個元素代表的是替換的個數 subnobj:編譯(轉換功能)
obj = re.compile('\d{3}') # 將正則表達式編譯成為一個 正則表達式對象,規(guī)則要匹配的是3個數字 ret = obj.search('abc123eeee') # 正則表達式對象調用search,參數為待匹配的字符串 ret1 = obj.findall('347982734729349827384')print(ret.group()) # 返回結果是 123print(ret1) # 返回結果是 ['347', '982', '734', '729', '349', '827', '384'] objfinditer:返回一個存放匹配結果的迭代器
ret = re.finditer('\d', 'ds3sy4784a') # finditer返回一個存放匹配結果的迭代器print(ret) # 返回<callable_iterator object at 內存地址>print(next(ret).group()) # 等價于ret.__next__(),超出迭代取值的范圍 直接報錯StopIterationprint([i.group() for i in ret]) # 查看剩余的左右結果 finditer?
擴展知識點:
?
1.?P可以給某一個正則表達式起別名
import reres = re.search('^[1-9] (\d{14})(\d{2}[0-9x])?$','110105199812067023')res = re.search('^[1-9] (?P<password>\d{14})(?P<username>\d{2}[0-9x])?$','110105199812067023')print(res.group()) # 返回值為110105199812067023print(res.group('password')) # 返回值為110105199812067print(res.group(1)) # 返回值為110105199812067print(res.group('username')) # 返回值為023print(res.group(2)) # 返回值為0232.?:取消權限,findall就不會優(yōu)先把匹配結果組里內容返回
ret1 = re.findall('www.(baidu|oldboy).com', 'www.oldboy.com')ret2 = re.findall('www.(?:baidu|oldboy).com', 'www.oldboy.com') # 忽略分組優(yōu)先的機制print(ret1,ret2) # ['oldboy']3.關于split的知識點
ret=re.split("\d+","eva3egon4yuan")print(ret) # 結果 : ['eva', 'egon', 'yuan'] ret1=re.split("(\d+)","eva3egon4yuan")print(ret1) # 結果 : ['eva', '3', 'egon', '4', 'yuan']?
轉載于:https://www.cnblogs.com/zhukaijian/p/11203705.html
總結
以上是生活随笔為你收集整理的python day15的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: CodeForces - 627A
- 下一篇: 流畅的python不适合初学者_学习《流