歡迎加入Linux_Python學習羣html
羣號:478616847java
目錄:node
模塊與導入介紹python
包的介紹
git
time &datetime模塊web
random正則表達式
os算法
sysshell
shutilexpress
json & pickle
xml處理
configparser
hashlib
subprocess
logging模塊
re正則表達式
模塊是某個功能代碼的集合,模塊是一種組織形式,它將彼此有關係的python代碼組織到一個個文件中,模塊能夠包含可執行代碼,
函數和類或者這些東西的組合。一個模塊建立以後, 你能夠從另外一個模塊中使用 import 語句導入這個模塊來使用。想一想看寫一個大
的項目的時候是否是有不少代碼,那麼咱們就須要使用模塊把這些代碼按照功能結構進行劃分,放在不一樣的目錄或者是包中。
形象的來講模塊就是有一些功能的py文件,咱們經過import能夠導入這個功能模塊,並使用它
模塊分爲三種:
內置模塊
三方開源模塊
自定義模塊
內置模塊:
在安裝完成python後,python自己就帶有庫,這個庫叫作python內置庫,那麼內置模塊也被稱之爲標準庫
三方開源模塊:
那麼python內置的模塊,有不少不能知足咱們的需求,那麼就會有不少人去本身寫模塊,而且把它開源出來,就是三方模塊、
那麼這些三方模塊,會有一些統一下載的地方,三方模塊下載地址 這個地址是pip的網站,裏面如今收錄了99886個三方模塊
這麼多的三方模塊得益於開源精神,因此咱們也是能夠在這個網站上上傳本身的模塊供你們使用。
自定義模塊:
自定義模塊就是你本身寫的代碼組成的功能,這些功能稱之爲一個模塊
導入模塊
模塊是有了,可是要在本身的代碼中使用模塊,是須要導入的,導入的方式有如下這麼幾種
1 import module 2 from module import xx 3 from module import xx as rename 4 from module import * 5 6 7 import sys 8 print(sys.path) 9 10 from sys import path 11 print(path) 12 13 from sys import path as new_path 14 print(new_path) 15 16 from sys import * 17 print(path) 18 print(argv)
import sys 直接導入sys模塊,想要用sys模塊的功能須要 sys.path (拿path舉例)
from sys import path 導入sys模塊中的path功能,使用時直接使用path
from sys import path as new_path 導入sys模塊中的path功能,並經過as 給path功能重命名,使用時直接使用新名字便可這個功能主要分防止功能名衝突
from sys import *導入sys模塊中的全部功能,使用時直接用功能名便可
導入自定義模塊
導入自定義模塊其實也很是簡單,首先在同級目錄下咱們有main.py和print_mode.py兩個文件,在print_mode python文件中定義一個函數內容以下
1 #!/usr/bin/env python 2 # -*- coding: utf-8 -*- 3 4 5 def new_print(arg): 6 print("\033[31m%s\033[0m"%arg)
而後咱們在main.py文件使用new_print這個函數,下面演示了上面的四種導入方法
1 #!/usr/bin/env python 2 # -*- coding: utf-8 -*- 3 import print_mode 4 print_mode.new_print("Hello world") 5 6 7 from print_mode import new_print 8 new_print("Hello world") 9 10 11 from print_mode import new_print as pr 12 pr("Hello world") 13 14 15 from print_mode import * 16 new_print("Hello world")
注意在上面我把同級目錄下加粗了,也就說這種方法只能導入同級目錄下的自定義模塊,下面介紹如何導入不是同級目錄下的模塊
一、首先咱們知道,操做系統有默認的環境變量,好比想要在cmd中使用python就須要在PATH環境變量中加入python的安裝目錄
那麼若是咱們想要導入其它目錄下自定義模塊,也要給python的PATH變量中加入模塊所在的目錄,個人目錄結構如圖
要知道的是咱們的程序在其它計算機上面使用是安裝到不一樣位置的,因此咱們確定不能再PATH環境變量中添加當前主機的程序位置
因此用os.path.abspath(__file__)獲得當前文件絕對路徑,而後咱們要獲得bin目錄的上層目錄,由於只有這樣才能找到mode目錄
經過os.path.dirname(os.path.abspath(__file__))獲得的是bin目錄的絕對路徑,也就是如今這句話獲得的是 bin目錄,咱們的
目的是獲得test目錄因此os.path.dirname(os.path.dirname(os.path.abspath(__file__))),獲得test目錄的絕對路徑了,接下來
把獲得的絕對路徑經過sys.path.appen加入到python環境變量裏面,那麼咱們就能夠導入mode目錄下的python_mode模塊了
1 #!/usr/bin/env python 2 # -*- coding: utf-8 -*- 3 4 import os,sys 5 6 print(os.path.abspath(__file__)) 7 print(os.path.dirname(os.path.abspath(__file__))) 8 print(os.path.dirname(os.path.dirname(os.path.abspath(__file__)))) 9 10 11 print("原:",sys.path) 12 base_dir = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 13 sys.path.append(base_dir) 14 print("新:",sys.path) 15 16 from mode import print_mode 17 print_mode.new_print("Hello world")
注意!若是在print_mode文件中有一個print()語句,那麼在print_mode文件被第一次導入的時候就會執行這個print語句,這是由於
第一次導入的時候會把print_mode文件內容加載到內存,爲了防止你重複導入,python的優化手段會把後續的import語句僅是對已經加
載大內存中的模塊對象增長了一次引用,不會從新執行模塊內的語句。
第三方模塊的安裝
安裝第三方模塊咱們可使用pip和源碼進行安裝,源碼安裝只須要作如下的操做
以paramiko模塊爲例,第三方模塊在安裝過程當中就在Python的PATH環境變量中,所以用法和內置模塊同樣
1 # pip install paramiko pip安裝方式 2 3 # pycrypto,因爲 paramiko 模塊內部依賴pycrypto,因此先下載安裝pycrypto 4 5 # 下載安裝 pycrypto 6 wget http://files.cnblogs.com/files/wupeiqi/pycrypto-2.6.1.tar.gz 7 tar -xvf pycrypto-2.6.1.tar.gz 8 cd pycrypto-2.6.1 9 python setup.py build 10 python setup.py install 11 12 # 進入python環境,導入Crypto檢查是否安裝成功 13 14 # 下載安裝 paramiko 15 wget http://files.cnblogs.com/files/wupeiqi/paramiko-1.10.1.tar.gz 16 tar -xvf paramiko-1.10.1.tar.gz 17 cd paramiko-1.10.1 18 python setup.py build 19 python setup.py install 20 21 # 進入python環境,import paramiko檢查是否安裝成功便可
更多運維中經常使用的第三方模塊請參考 Python自動化運維
包是一種經過使用" .模塊名 "來組織python模塊名稱空間的方式,其實python中的包 就是一個包含__init__.py文件的目錄。模塊稱之爲文件
那麼包就是文件的集合,在咱們使用目錄來存儲模塊,會形成模塊名衝突的問題,那麼包就能夠有效地避免模塊名衝突的問題,在學習包以前
首先建立了一個根目錄目錄和app,bin,config這三個包,每一個包裏都有py文件
1 #app_one 2 def conf_app_one(): 3 print("From app_one") 4 5 #app_two 6 def conf_app_two1(): 7 print("From 1 app_two.py") 8 9 def conf_app_two2(): 10 print("From 2 app_two.py") 11 12 #conf 13 def conf_func(): 14 print("From conf.py")
導入包
包的導入也分爲import,和from...import,import導入語句也是導入同級目錄的因此這裏不作演示 不管是import形式仍是from...import形式,凡是在導入語
句中(而不是在使用時)遇到帶點的,都是關於包纔有的導入語法,而且from後面的import導入的模塊是不能帶點的,因此點的左邊必須是一個包
錯誤方法:from aa import bb.c
第一次導入包的時候,會執行包中的 __init__.py文件,首先咱們能夠在config模塊中的 __init__.py 寫一句 print,而後在main。py中導入 config模塊試一下
1 #!/usr/bin/env python 2 # -*- coding:utf-8 -*- 3 4 import os,sys 5 path = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 6 sys.path.append(path) 7 8 from config import conf
當咱們運行main.py 後就觸發了在config模塊中的 __init__.py 的print語句
__all__
那麼這個__init__.py還能幹什麼事呢?
此次咱們導入 app包下的模塊,看看*能不能把app下面的文件所有導入進來
1 #!/usr/bin/env python 2 # -*- coding:utf-8 -*- 3 4 5 #main文件 6 import os,sys 7 path = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 8 sys.path.append(path) 9 10 from app import * 11 12 app_one.conf_app_one() 13 app_two.conf_app_two1()
然而咱們一運行發現報錯,說app_one沒有定義!
這不科學,安裝道理說from app import *應該導入 app包下的全部py文件啊!其實在app下的__init__文件中加入__all__ = ["app_one","app_two"],就能夠這樣調用了。
最後咱們來看正常導入的方式
1 #!/usr/bin/env python 2 # -*- coding:utf-8 -*- 3 4 import os,sys 5 path = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 6 sys.path.append(path) 7 8 from app import app_two 9 app_two.conf_app_two1() 10 11 from app import app_two as two 12 two.conf_app_two2() 13 14 from app.app_one import * 15 conf_app_one()
pyc文件
有一天我忽然打開包的目錄,突然發現,目錄中多出了__pycache__的文件夾,裏面有.pyc的文件,在好奇心的驅使下我百度出它的真面目
原來python爲了提升模塊的加載速度,Python緩存編譯的版本,每一個模塊在__pycache__目錄下有着以module.version.pyc的形式命名
的文件,這些文件名包含了python的版本號,模塊名,如CPython版本3.5,而且Python會檢查源文件的修改時間與編譯的版本進行對比,
若是過時就須要從新編譯。這是徹底自動的過程。不一樣的版本編譯後的pyc文件不一樣,2.5編譯的pyc文件不能到3.5上執行,而且pyc文件是
能夠反編譯的,於是它的出現僅僅是用來提高模塊的加載速度的。
接下來開始學習經常使用的內置模塊,內置模塊就是集成在python中的工具包,咱們要學習經常使用的工具包的用法,這些用法很是簡單
在平時的代碼中,常常要與實際打交道 與時間處理有關的模塊就包括:time,datetime以及calendar這裏講解前兩個模塊
Time模塊
python中一般有這幾種形式來表示時間:一、時間戳 二、格式化的時間字符串 三、元祖
一、time.localtime()會經過time.struct_time的class類轉換成特殊時間的格式,括號中能夠傳入時間戳,若是不傳入則用的是當前時間,咱們能夠經過下標取出對應的值
time.struct_time(tm_year=2017, tm_mon=3, tm_mday=10, tm_hour=15, tm_min=53, tm_sec=53, tm_wday=4, tm_yday=69, tm_isdst=0)
二、time.gmtime()與time.localtime()方法相似,只不過會把當前時間轉換成0時區的時間
time.struct_time(tm_year=2017, tm_mon=3, tm_mday=10, tm_hour=16, tm_min=1, tm_sec=16, tm_wday=4, tm_yday=69, tm_isdst=0)
time.struct_time(tm_year=2017, tm_mon=3, tm_mday=10, tm_hour=8, tm_min=1, tm_sec=16, tm_wday=4, tm_yday=69, tm_isdst=0)
三、time.time():返回當前時間的時間戳。
四、time.mktime(t):將一個struct_time轉化爲時間戳。
五、time.sleep(secs):線程推遲指定的時間運行。單位爲秒,能夠是小數
六、time.clock():在UNIX系統上,它返回的是「進程時間」,它是用秒錶示的浮點數(時間戳)。而在WINDOWS中,第一次調用,返回的是進程運行的實際時間。
而第二次以後的調用是自第一次調用之後到如今的運行時間。
七、time.asctime([t]):把一個表示時間的元組或者struct_time表示爲這種形式:'Sun Jun 20 23:21:05 1993'。若是沒有參數,將會將time.localtime()做爲參數傳入。
八、time.ctime([secs]):把一個時間戳(按秒計算的浮點數)轉化爲time.asctime()的形式。若是參數未給或者爲None的時候,將會默認time.time()爲參數。
它的做用至關於time.asctime(time.localtime(secs))。
輸出自定義的日期格式
1 import time 2 3 print(time.strftime("%Y:%m:%d,%H",time.localtime(time.time())))
能夠看到其中雙引號的內容就是調用了下面的格式
datetime模塊
這個模塊能夠理解爲data和time兩個部分,主要用於時間的加減,也能夠計算時間差
1 import datetime 2 import time 3 4 #返回 當前時間 5 print(datetime.datetime.now()) 6 # 時間戳直接轉成日期格式 2016-08-19 7 print(datetime.date.fromtimestamp(time.time()) ) 8 9 #當前時間+3天 10 print(datetime.datetime.now() + datetime.timedelta(3)) 11 #當前時間-3天 12 print(datetime.datetime.now() + datetime.timedelta(-3)) 13 #當前時間+3小時 14 print(datetime.datetime.now() + datetime.timedelta(hours=3)) 15 #當前時間+30分 16 print(datetime.datetime.now() + datetime.timedelta(minutes=30)) 17 18 #時間替換 19 c_time = datetime.datetime.now() 20 print(c_time.replace(minute=3,hour=2)) 21 22 23 #計算時間差,返回天數 24 datas = "2016-08-19" 25 def Repayment(past_time): 26 def conversion(str_data):#把每一個元素變成int類型 27 data_list = str_data.split("-") 28 for i in data_list:data_list[data_list.index(i)] = int(i) 29 return data_list 30 #獲得新老時間的列表 31 new_time_list = conversion(time.strftime("%Y-%m-%d",time.localtime(time.time()))) 32 past_time_list = conversion(past_time) 33 n_time = datetime.datetime(new_time_list[0],new_time_list[1],new_time_list[2]) 34 p_time = datetime.datetime(past_time_list[0],past_time_list[1],past_time_list[2]) 35 return ((n_time - p_time).days) 36 print(Repayment(datas))
生成隨機數
1 #!/usr/bin/env python 2 3 import random 4 5 #生成一個0到1的隨機浮點數 6 print(random.random()) 7 8 #用於生成一個指定範圍內的隨機符點數 9 print( random.uniform(10, 20)) 10 print( random.uniform(10, 20)) 11 12 #用於生成一個指定範圍內的整數。 13 print(random.randint(10, 20)) 14 15 #指定範圍內,按指定基數遞增的集合中 獲取一個隨機數。 16 #例子中也就是隻會從 10 12 14 ... 18取得隨機數,第三個參數爲2的時候也就是取偶數 17 print(random.randrange(10,20, 2)) 18 19 #從序列中獲取一個隨機元素。 20 data_str = "I love Python" 21 data_list = [1,2,3,4,5,6] 22 data_tuple = ("A","B","C","D","E") 23 print(random.choice(data_str)) 24 print(random.choice(data_list)) 25 print(random.choice(data_tuple)) 26 27 #用於將一個列表中的元素打亂。 28 data_list = [1,2,3,4,5,6] 29 random.shuffle(data_list) 30 print(data_list) 31 32 #從指定序列中隨機獲取指定長度的片段 33 data_list = [1,2,3,4,5,6] 34 print(random.sample(data_list,3))
小例子:生成隨機的驗證碼
1 #!/usr/bin/env python 2 3 import random 4 # 初版 5 def code(number): 6 ''' 7 隨機數生成器 8 ''' 9 number_check = '' 10 for i in range(0,number): 11 number_curr = random.randrange(0,5) 12 if number_curr != i: 13 number_temp = chr(random.randint(97,122)) 14 else: 15 number_temp = random.randint(0,9) 16 number_check += str(number_temp) 17 return number_check 18 print(code(5)) 19 20 # 第二版 21 import string 22 source = string.digits + string.ascii_uppercase + string.ascii_lowercase 23 print("".join(random.sample(source, 4)))
os模塊以前咱們接觸了與文件相關的發放,os模塊還有不少與操做系統交互的函數
1 os.getcwd() 獲取當前工做目錄,即當前python腳本工做的目錄路徑 2 os.chdir("dirname") 改變當前腳本工做目錄;至關於shell下cd 3 os.curdir 返回當前目錄: ('.') 4 os.pardir 獲取當前目錄的父目錄字符串名:('..') 5 os.makedirs('dirname1/dirname2') 可生成多層遞歸目錄 6 os.removedirs('dirname1') 若目錄爲空,則刪除,並遞歸到上一級目錄,如若也爲空,則刪除,依此類推 7 os.mkdir('dirname') 生成單級目錄;至關於shell中mkdir dirname 8 os.rmdir('dirname') 刪除單級空目錄,若目錄不爲空則沒法刪除,報錯;至關於shell中rmdir dirname 9 os.listdir('dirname') 列出指定目錄下的全部文件和子目錄,包括隱藏文件,並以列表方式打印 10 os.remove() 刪除一個文件 11 os.rename("oldname","newname") 重命名文件/目錄 12 os.stat('path/filename') 獲取文件/目錄信息 13 os.sep 輸出操做系統特定的路徑分隔符,win下爲"\\",Linux下爲"/" 14 os.linesep 輸出當前平臺使用的行終止符,win下爲"\t\n",Linux下爲"\n" 15 os.pathsep 輸出用於分割文件路徑的字符串 win下爲;,Linux下爲: 16 os.name 輸出字符串指示當前使用平臺。win->'nt'; Linux->'posix' 17 os.system("bash command") 運行shell命令,直接顯示 18 os.environ 獲取系統環境變量 19 os.path.abspath(path) 返回path規範化的絕對路徑 20 os.path.split(path) 將path分割成目錄和文件名二元組返回 21 os.path.dirname(path) 返回path的目錄。其實就是os.path.split(path)的第一個元素 22 os.path.basename(path) 返回path最後的文件名。如何path以/或\結尾,那麼就會返回空值。即os.path.split(path)的第二個元素 23 os.path.exists(path) 若是path存在,返回True;若是path不存在,返回False 24 os.path.isabs(path) 若是path是絕對路徑,返回True 25 os.path.isfile(path) 若是path是一個存在的文件,返回True。不然返回False 26 os.path.isdir(path) 若是path是一個存在的目錄,則返回True。不然返回False 27 os.path.join(path1[, path2[, ...]]) 將多個路徑組合後返回,第一個絕對路徑以前的參數將被忽略 28 os.path.getatime(path) 返回path所指向的文件或者目錄的最後存取時間 29 os.path.getmtime(path) 返回path所指向的文件或者目錄的最後修改時間 30 os.path.normpath(path) #規範化路徑,轉換path的大小寫和斜槓
sys模塊也是比較經常使用的模塊,好比獲取命令執行python是後面的參數
1 sys.argv 命令行參數List,第一個元素是程序自己路徑 2 sys.exit(n) 退出程序,正常退出時exit(0) 3 sys.version 獲取Python解釋程序的版本信息 4 sys.maxint 最大的Int值 5 sys.path 返回模塊的搜索路徑,初始化時使用PYTHONPATH環境變量的值 6 sys.platform 返回操做系統平臺名稱
shutil是一種高層次的文件操做工具,提供了大量的文件高級操做(能夠用print(help(shutil))來查看),好比 拷貝刪除,壓縮等等
1 #!/usr/bin/env python 2 3 import shutil 4 5 #一、將文件拷貝到另外一個文件中 6 shutil.copyfileobj(open('test','r'), open('test2', 'w')) 7 8 #二、拷貝文件 9 shutil.copyfile('test', 'test2.conf') 10 11 #三、拷貝權限 內容、組、用戶均不變(目標文件必須存在) 12 shutil.copymode('test', 'test2.conf') 13 14 #四、僅拷貝狀態的信息,包括:mode bits, atime, mtime, flags(目標文件必須存在) 15 shutil.copystat('test', 'test2.conf') 16 17 #五、拷貝文件和權限 18 shutil.copy('test', 'test3') 19 20 #六、拷貝文件和狀態信息 21 shutil.copy2('test', 'test3') 22 23 #七、遞歸的去拷貝文件夾 24 shutil.copytree('testlist', 'test2list', ignore=shutil.ignore_patterns('main.py',)) 25 """目標目錄不能存在,注意對test2list目錄父級目錄要有可寫權限, 26 ignore的意思是排除,這裏表示不拷貝main.py文件,多個能夠用逗號隔開,也能夠用*.py""" 27 28 #拷貝軟鏈接 29 shutil.copytree('f1', 'f2', symlinks=True, ignore=shutil.ignore_patterns('*.pyc')) 30 #一般的拷貝都把軟鏈接拷貝成硬連接,即對待軟鏈接來講,建立新的文件 31 32 #八、遞歸的去刪除文件 33 shutil.rmtree('test2list') 34 35 #九、遞歸的去移動文件,它相似mv命令,其實就是重命名。 36 shutil.move("testlist", "testlist2")
壓縮shutil.make_archive(base_name, format,...)
建立壓縮包並返回文件路徑,例如:zip、tar
1 #!/usr/bin/env python 2 3 import shutil 4 5 #打包當前目錄下的testlist目錄,打包成a_bk.zip 6 #支持方法"zip", "tar", "bztar" "gztar". 7 tar = shutil.make_archive("a_bk","zip",root_dir="./testlist") 8 9 #把打包結果文件剛在/mnt/目錄下 10 tar2 = shutil.make_archive("/mnt/a_bk","gztar",root_dir="./testlist")
shutil 對壓縮包的處理是調用 ZipFile 和 TarFile 兩個模塊來進行的
在程序運行的過程當中,變量都是在變化的,而且當程序結束後變量將消失,那麼爲了讓程序下次運行的時候還能夠用上次的變量,就須要對這些變量,字典,列表經過
序列化保存在文件中,下一次讀取文件中的內容進行反序列化就可獲得上次運行時的變量數據,那麼json和pickle是用於數據序列化的模塊,有些童鞋會常常聽見開發說
,這個Api返回的是一串json,因此json就是不一樣平臺直接傳輸數據的,由於在java中在html中都支持json格式的數據
Json和Pickle 都提供了四個功能:dumps、dump、loads、load
Json
1 #!/usr/bin/env python 2 import json 3 4 #-----------序列化---------# 5 dic = {"name":'aaa',"age":22,} 6 lis = [1,2,3,"4"] 7 8 with open("test","w") as file: 9 file.write(json.dumps(dic)) 10 with open("test2","w") as file: 11 json.dump(lis,file) 12 13 #----------反序列化---------# 14 with open("test","r") as file: 15 data_dic = json.loads(file.read()) 16 with open("test2","r") as file: 17 data_lis = json.load(file) 18 print(type(data_lis),":",data_lis) 19 print(type(data_dic),":",data_dic)
注!Json不能保存函數和類對象,可是Pickle能夠
Pickle,是python獨有的,其它語言並不支持,而且保存的數據類時要用bytes方式寫入
1 #!/usr/bin/env python 2 import pickle 3 4 #-----------序列化---------# 5 dic = {"name":'aaa',"age":22,} 6 def func(): 7 return "Hello" 8 9 with open("test","wb") as file: 10 file.write(pickle.dumps(dic)) 11 with open("test2","wb") as file: 12 pickle.dump(func,file) 13 14 #----------反序列化---------# 15 with open("test","rb") as file: 16 data_dic = pickle.loads(file.read()) 17 with open("test2","rb") as file: 18 data_func = pickle.load(file) 19 print(type(data_func),":",data_func) 20 print(data_func()) 21 print(type(data_dic),":",data_dic)
xml也是實現不一樣語言或程序之間的數據交互,跟json差很少,它是誕生在json以前,現在不少傳統公司和金融行業的系統主要的
接口仍是xml
xml數據格式以下
1 <?xml version='1.0' encoding='utf-8'?> 2 <userdata> 3 <name Name="XiaoMing"> 4 <age>22</age> 5 <gender>Men</gender> 6 </name> 7 <name Name="XiaoHong"> 8 <age>19</age> 9 <gender>Women</gender> 10 </name> 11 </userdata>
建立上面內容的xml文件
1 #生成 最外層的<userdata> 2 new_xml = ET.Element("userdata") 3 4 #生成<name Name="XiaoMing"> 5 name1 = ET.SubElement(new_xml,"name",attrib={"Name":"XiaoMing"}) 6 #生成<name Name="XiaoMing">中的<age>22</age> 7 age = ET.SubElement(name1,"age") 8 age.text = "22" 9 #生成<name Name="XiaoMing">中的<gender>Men</gender> 10 gender = ET.SubElement(name1,"gender") 11 gender.text = "Men" 12 13 #生成<name Name="XiaoHong"> 14 name2 = ET.SubElement(new_xml,"name",attrib={"Name":"XiaoHong"}) 15 #生成<name Name="XiaoHong">中的<age>19</age> 16 age = ET.SubElement(name2,"age") 17 age.text = '19' 18 #生成<name Name="XiaoHong">中的<gender>Women</gender> 19 gender = ET.SubElement(name2,"gender") 20 gender.text = "Women" 21 22 et = ET.ElementTree(new_xml) #生成文檔對象 23 et.write("test.xml", encoding="utf-8",xml_declaration=True)#寫入
讀取xml文件內容
1 #獲取最外層的<userdata> 2 tree = ET.parse("test.xml") 3 root = tree.getroot() 4 print(root.tag) 5 print("-----------------遍歷xml文檔------------------") 6 #遍歷xml文檔 7 for child in root: 8 print(child.tag,child.attrib)#打印<name Name="XiaoMing">和<name Name="XiaoHong"> 9 for i in child: 10 print(i.tag,i.text)#分別打印年齡和性別 11 12 print("-----------------只遍歷age 節點------------------") 13 #只遍歷age 節點 14 for node in root.iter("age"): 15 print(node.tag,node.text)
更改刪除xml文件內容
1 import xml.etree.ElementTree as ET 2 3 print("--------------------年齡加1------------------") 4 tree = ET.parse("test.xml") 5 root = tree.getroot() 6 7 for node in root.iter('age'): 8 node.text = str(int(node.text) + 1)#年齡加一 9 node.set("updated","yes") #增長屬性 updated=「yex」 10 tree.write("test.xml")#寫入 11 12 13 print("----------------刪除年齡大於20的-------------") 14 tree = ET.parse("test.xml") 15 root = tree.getroot() 16 17 for country in root.findall('name'):#循環name標籤,[<Element 'name' at 0x009F4180>, <Element 'name' at 0x009F4240>] 18 rank = int(country.find('age').text)#獲取name標籤下的年齡 19 if rank > 20:#判斷年齡是否大於20 20 root.remove(country)#若是大則刪除 21 tree.write('test.xml')#寫入
這個內置模塊呢通常用處用來作配置文件的操做,能夠操做如下格式的文件
1 [www.test.org] 2 user = test 3 port = 20012 4 5 [www.test2.org] 6 user = test2 7 port = 20011 8 forwardx11 = no
語法:讀操做
-read(filename) 直接讀取文件內容
-sections() 獲得全部的section,並以列表的形式返回
-options(section) 獲得該section的全部option
-items(section) 獲得該section的全部鍵值對
-get(section,option) 獲得section中option的值,返回爲string類型
-getint(section,option) 獲得section中option的值,返回爲int類型
寫操做
-add_section(section) 添加一個新的section
-set( section, option, value) 對section中的option進行設置
示例代碼
1 #!/usr/bin/env python 2 3 import configparser 4 import time 5 6 conf = configparser.ConfigParser() 7 conf.read('conf') 8 9 print("----------------讀----------------") 10 #獲得全部的section,並以列表的形式返回 11 print(conf.sections()) 12 #獲得該section的全部option 13 print(conf.options('www.test.org')) 14 #獲得該section的全部鍵值對 15 print(conf.items('www.test2.org')) 16 print(conf.get('www.test2.org',"User"))#獲得section中option的值,返回爲string類型 17 time.sleep(2) 18 19 print("----------------改----------------") 20 conf.set('www.test2.org','port',"1234") 21 conf.write(open('conf', "w")) 22 time.sleep(2) 23 24 print("----------------判斷---------------") 25 print(conf.has_section('www.test2.org')) 26 time.sleep(2) 27 28 print("----------------刪----------------") 29 #刪除section中的option 30 conf.remove_option('www.test.org','port') 31 #刪除section 32 conf.remove_section('www.test.org') 33 conf.write(open('conf', "w")) 34 time.sleep(2) 35 36 print("----------------寫----------------") 37 #添加section 38 conf.add_section('www.test3.org') 39 #添加section中的option 40 conf.set('www.test3.org','port',"222") 41 conf.write(open('conf', "w"))
hashlib在python3中代替了MD5和sha模塊,主要提供了SHA1, SHA224, SHA256, SHA384, SHA512 ,MD5 算法,在python3中已經廢棄了
md5和sha模塊,其中最爲經常使用的MD5算法,咱們常常看到下載一個光盤鏡像的時候,後面會告訴你一個MD5值,這個就是用來作文件完整性驗證的
因此同一種字符串計算出來的MD5值是同樣的
特色:一、相同的內容hash運輸的結果是相同的二、這種計算是不可逆的三、相同算法,不管校驗多長的數據,獲得的哈希值長度固定。
以常見的摘要算法MD5爲例,計算出一個字符串的MD5值:
1 #!/usr/bin/env python 2 3 import hashlib 4 5 #首先定義一個hashlib的對象 6 ha = hashlib.md5()#用的md5加密方式,這裏還能夠用SHA1, SHA224, SHA256, SHA384, SHA512算法 7 ha.update("Hello".encode("utf-8")) 8 print(ha.hexdigest())#返回16進制 9 print(ha.digest())#返回二進制 10 #結果 8b1a9953c4611296a827abf8c47804d7 b"\x8b\x1a\x99S\xc4a\x12\x96\xa8'\xab\xf8\xc4x\x04\xd7"
subprocess用於執行本地命令,它是經過管道的形式,鏈接到他們的輸入/輸出/錯誤,並得到他們的返回代碼。
示例代碼:(官方介紹)
1 import subprocess 2 #執行命令,若是命令結果爲0,就正常返回,不然拋異常 3 retcode = subprocess.call(["ls", "-l"]) 4 5 #接收字符串格式命令,返回元組形式,第1個元素是執行狀態,第2個是命令結果 6 results = subprocess.getstatusoutput('ls /bin/ls') 7 print(results) 8 9 #接收字符串格式命令,並返回結果 10 print(subprocess.getoutput('ls /bin/ls')) 11 12 #執行命令,並返回結果,注意是返回結果,不是打印,下例結果返回給res 13 res=subprocess.check_output(['ls','-l']) 14 print(res) 15 16 #調用subprocess.run(...)是推薦的經常使用方法,在大多數狀況下能知足需求, 17 subprocess.run(["ls", "-l", "/dev/null"], stdout=subprocess.PIPE)
其實上面的方法都是對Popen的封裝subprocess模塊中只定義了Popen這個類,咱們可使用Popen來建立進程,並與進程進行復雜的交互。
這個模塊將取代 os.system 和 os.spawn*,Popen這個類其中能夠跟不少參數。
args |
shell命令,能夠是字符串或者序列類型(如:list,元組) |
bufsize |
指定緩衝: 0:無緩衝 1:行緩衝 其餘正值:緩衝區大小 負值:採用默認系統緩衝(通常是全緩衝) |
executable |
通常不用吧,args字符串或列表第一項表示程序名 |
stdin stdout stderr |
分別表示程序的標準輸入、輸出、錯誤句柄 |
preexec_fn |
鉤子函數, 只在Unix平臺下有效,用於指定一個可執行對象(callable object),它將在子進程運行以前被調用 |
close_fds |
unix 下執行新進程前是否關閉0/1/2以外的文件 |
在windows平臺下,若是close_fds被設置爲True,則新建立的子進程將不會繼承父進程的輸入、輸出、錯誤管道。 |
|
shell |
爲真的話 unix下至關於在命令前面添加了 "/bin/sh」 」-c」 window下,至關於添加"cmd.exe /c" |
cwd |
設置工做目錄 |
env |
設置環境變量 |
universal_newlines |
不一樣系統的換行符不一樣,True -> 則統一使用 \n 爲換行符 |
startupinfo |
window下傳遞給CreateProcess的結構體 |
creationflags |
只在windows下有效 |
Popen使用方法
但若是你須要進行一些複雜的與系統的交互的話,則需呀Popen,語法以下
1 import subprocess 2 3 subprocess.Popen(["ls","test"]) 4 subprocess.Popen("cat test.txt", shell=True) 5 p = subprocess.Popen("ls test",stdin=subprocess.PIPE,stdout=subprocess.PIPE,shell=True) 6 p.stdout.read() 7 8 #須要交互的命令示例 9 obj = subprocess.Popen(["python"], stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE) 10 obj.stdin.write('print(1) \n ') 11 obj.stdin.write('print(2) \n ') 12 obj.stdin.write('print(3) \n ') 13 obj.stdin.write('print(4) \n ') 14 15 out_error_list = obj.communicate(timeout=10) 16 print(out_error_list)
1 import subprocess 2 3 mypass = '123'#密碼 4 5 echo = subprocess.Popen(['echo',mypass],stdout=subprocess.PIPE,) 6 #命令 7 sudo = subprocess.Popen(['sudo','-S','iptables','-L'],stdin=echo.stdout,stdout=subprocess.PIPE,) 8 9 end_of_pipe = sudo.stdout 10 print("Password ok \n Iptables Chains %s" % end_of_pipe.read())
logging模塊主要針對日誌,在程序中須要日誌,好幫助咱們進行統計以及問題分析,logging的日誌能夠分爲 debug()
, info()
, warning()
, error()
and critical() 5個級別
下面來看一下用法
1 import logging 2 3 logging.warning("user test attempted wrong password more than 3 times") 4 logging.critical("server is down") 5 logging.error("File cannot be opened")
咱們發現有logging模塊有info級別有error級別,那麼看看這些級別表明的意思
1 import logging 2 3 print(logging.NOTSET) #0 4 print(logging.DEBUG) #10 5 print(logging.INFO) #20 6 print(logging.WARNING)#30 7 print(logging.ERROR) #40 8 print(logging.CRITICAL)#50
把日誌寫入文件
1 import logging 2 3 logging.basicConfig(filename='test.log',level=logging.INFO) 4 logging.debug('debug') 5 logging.info('info') 6 logging.warning("warning")
咱們能夠發現debug信息是沒有寫入日誌的level
=
logging.INFO是定義了最低寫入日誌的級別,只有比日誌是INFO或比INFO級別更高的日誌纔會被紀錄到文件裏
上面的日誌中少了時間,咱們能夠定義一些日誌格式來實現本身的需求
1 import logging 2 3 logging.basicConfig(level=logging.DEBUG, 4 format='%(asctime)s %(name)s %(levelname)s %(message)s', 5 datefmt='[%Y-%m-%d %H:%M:%S]', 6 filename='test.log', 7 filemode='a') 8 9 logging.warning('warning')
在自定義日誌中,format表示日誌格式,用到的就是下面截圖中的功能,filename是日誌的文件名,filemode是打開日誌的格式,默認是w打開因此要是想追加
日誌就須要把模式改爲a
日誌格式
若是想同時把log打印在屏幕和文件日誌裏,就須要瞭解一點複雜的知識了
Python 使用logging模塊記錄日誌涉及四個主要類,使用官方文檔中的歸納最爲合適:
1 logger 2 每一個程序在輸出信息以前都要得到一個Logger。Logger一般對應了程序的模塊名,好比聊天工具的圖形界面模塊能夠這樣得到它的Logger: 3 LOG=logging.getLogger(」chat.gui」) 4 而核心模塊能夠這樣: 5 LOG=logging.getLogger(」chat.kernel」) 6 7 Logger.setLevel(lel):指定最低的日誌級別,低於lel的級別將被忽略。debug是最低的內置級別,critical爲最高 8 Logger.addFilter(filt)、Logger.removeFilter(filt):添加或刪除指定的filter 9 Logger.addHandler(hdlr)、Logger.removeHandler(hdlr):增長或刪除指定的handler 10 Logger.debug()、Logger.info()、Logger.warning()、Logger.error()、Logger.critical():能夠設置的日誌級別 11 12 13 14 handler 15 16 handler對象負責發送相關的信息到指定目的地。Python的日誌系統有多種Handler可使用。有些Handler能夠把信息輸出到控制檯,有些Logger能夠把信息輸出到文件,還有些 Handler能夠把信息發送到網絡上。若是以爲不夠用,還能夠編寫本身的Handler。能夠經過addHandler()方法添加多個多handler 17 Handler.setLevel(lel):指定被處理的信息級別,低於lel級別的信息將被忽略 18 Handler.setFormatter():給這個handler選擇一個格式 19 Handler.addFilter(filt)、Handler.removeFilter(filt):新增或刪除一個filter對象 20 21 22 每一個Logger能夠附加多個Handler。接下來咱們就來介紹一些經常使用的Handler: 23 1) logging.StreamHandler 24 使用這個Handler能夠向相似與sys.stdout或者sys.stderr的任何文件對象(file object)輸出信息。它的構造函數是: 25 StreamHandler([strm]) 26 其中strm參數是一個文件對象。默認是sys.stderr 27 28 29 2) logging.FileHandler 30 和StreamHandler相似,用於向一個文件輸出日誌信息。不過FileHandler會幫你打開這個文件。它的構造函數是: 31 FileHandler(filename[,mode]) 32 filename是文件名,必須指定一個文件名。 33 mode是文件的打開方式。參見Python內置函數open()的用法。默認是’a',即添加到文件末尾。 34 35 3) logging.handlers.RotatingFileHandler 36 這個Handler相似於上面的FileHandler,可是它能夠管理文件大小。當文件達到必定大小以後,它會自動將當前日誌文件更名,而後建立 一個新的同名日誌文件繼續輸出。好比日誌文件是chat.log。當chat.log達到指定的大小以後,RotatingFileHandler自動把 文件更名爲chat.log.1。不過,若是chat.log.1已經存在,會先把chat.log.1重命名爲chat.log.2。。。最後從新建立 chat.log,繼續輸出日誌信息。它的構造函數是: 37 RotatingFileHandler( filename[, mode[, maxBytes[, backupCount]]]) 38 其中filename和mode兩個參數和FileHandler同樣。 39 maxBytes用於指定日誌文件的最大文件大小。若是maxBytes爲0,意味着日誌文件能夠無限大,這時上面描述的重命名過程就不會發生。 40 backupCount用於指定保留的備份文件的個數。好比,若是指定爲2,當上面描述的重命名過程發生時,原有的chat.log.2並不會被改名,而是被刪除。 41 42 43 4) logging.handlers.TimedRotatingFileHandler 44 這個Handler和RotatingFileHandler相似,不過,它沒有經過判斷文件大小來決定什麼時候從新建立日誌文件,而是間隔必定時間就 自動建立新的日誌文件。重命名的過程與RotatingFileHandler相似,不過新的文件不是附加數字,而是當前時間。它的構造函數是: 45 TimedRotatingFileHandler( filename [,when [,interval [,backupCount]]]) 46 其中filename參數和backupCount參數和RotatingFileHandler具備相同的意義。 47 interval是時間間隔。 48 when參數是一個字符串。表示時間間隔的單位,不區分大小寫。它有如下取值: 49 S 秒 50 M 分 51 H 小時 52 D 天 53 W 每星期(interval==0時表明星期一) 54 midnight 天天凌晨
實現的代碼
1 import logging 2 3 #定義文件日誌格式 4 logging.basicConfig(level=logging.DEBUG, 5 format='%(asctime)s %(name)s %(levelname)s %(message)s', 6 datefmt='[%Y-%m-%d %H:%M:%S]', 7 filename='test.log', 8 filemode='a') 9 10 #create logger建立日誌記錄器 11 logger = logging.getLogger() 12 logger.setLevel(logging.DEBUG) 13 14 # create console handler and set level to debug 15 #定義輸出級別爲DEBUG 16 ch = logging.StreamHandler() 17 ch.setLevel(logging.DEBUG) 18 19 # create formatter 建立日誌輸出的格式 20 formatter = logging.Formatter('%(asctime)s %(name)s - %(levelname)s - %(message)s', 21 datefmt='[%Y-%m-%d %H:%M:%S]') 22 23 # add formatter to ch 綁定日誌輸出格式 24 ch.setFormatter(formatter) 25 26 # add ch to logger 綁定到日誌記錄器 27 logger.addHandler(ch) 28 29 #調用日誌 30 logger.debug('debug message') 31 logger.info('info message') 32 logger.warn('warn message') 33 logger.error('error message') 34 logger.critical('critical message')
正則表達式相信不少人都熟悉了,在python中正則表達式的支持是經過re(regular expression)模塊來支持的
下面來熟悉下正則中的幾個概念:
一、通配符
通配符是一種特殊語句可使用它來代替一個或多個真正的字符好比‘ . ’點,他就能夠代替任意的字符除了換行符,.python就能夠等於xpython、+python等等
二、字符集
既然通配符」. 」能夠表示一個任意的字符,那麼字符集就能夠表示一個字符的範圍例如[a-z]就能夠表示a-z的任意一個字符,還能夠[a-zA-Z0-9]來表示大小寫字母
和數字,咱們還能夠將它來轉義[^a]就是除了a的意思
注意的是這裏的轉意符不是單個\而是雙\\
爲何使用兩個反斜線?這是爲了經過解釋器進行轉義,須要進行兩個級別的轉義:1.經過解釋器的轉義;2.經過 re 模塊轉義。若是不想使用兩個反斜線,能夠考
慮使用原始字符串,如:r'python\.org'。
三、選擇符
爲何存在選擇符呢?主要緣由是假如咱們想匹配兩個字符串如「aaa」,「bbb」,咱們就須要使用管道符(|)所以在匹配的時候就能夠寫成‘aaa|bbb’,當有的時候不
須要匹配這兩的時候假如只須要匹配字符串「aaa」或者「bbb」就能夠寫成「p(aaa|bbb)」
四、表示個數(重複模式)
表示個數顧名思義就是來表示這個字符有多少個的意思主要模式(pattern)有:
(pattern)*:表示這個模式能夠重複0次或者屢次
(pattern)+:表示容許這個模式出現一次或者屢次
(pattern){m,n}:表示容許這個模式重複m到n次
(pattern){n}:表示重複n次
(pattern){n,} :表示重複n或者更屢次,最低重複n次
五、表示開頭和結尾
當咱們要匹配以什麼什麼開頭或者以什麼什麼結尾是表示開頭咱們可使用‘^a’表示以a開頭,’$a‘表示以a結尾
re模塊提供的功能:
1 、compile(pattern[, flags]) 根據包含正則表達式的字符串建立模式對象
2 、search(pattern, string[, flags]) 在字符串中尋找模式
3 、match(pattern, string[, flags]) 在字符串的開始處匹配模式
4 、split(pattern, string[, maxsplit=0]) 根據模式的匹配項來分割字符串
5 、findall(pattern, string) 列出字符串中模式的全部匹配項
6 、sub(pat, repl, string[, count=0]) 將字符串中全部pat的匹配項用repl替換
7 、escape(string) 將字符串中全部特殊正則表達式字符轉義
語法:
re.match(pattern, string, flags=0)
pattern:匹配的正則表達式
string:要匹配的字符串。
flags:標誌位,用於控制正則表達式的匹配模式,如:是否區分大小寫,多行匹配等等(例子:print(re.match("^[a]+[d]+","aADdsdaa",flags=re.IGNORECASE)))
1 I = IGNORECASE = sre_compile.SRE_FLAG_IGNORECASE # ignore case 2 使匹配對大小寫不敏感;字符類和字符串匹配字母時忽略大小寫。舉個例子,[A-Z]也能夠匹配小寫字母,Spam 能夠匹配 "Spam", "spam", 或 "spAM"。這個小寫字母並不考慮當前位置。 3 4 L = LOCALE = sre_compile.SRE_FLAG_LOCALE # assume current 8-bit locale 5 影響 "w, "W, "b, 和 "B,這取決於當前的本地化設置。 6 locales 是 C 語言庫中的一項功能,是用來爲須要考慮不一樣語言的編程提供幫助的。舉個例子,若是你正在處理法文文本,你想用 "w+ 來匹配文字,但 "w 只匹配字符類 [A-Za-z];它並不能匹配 "é" 或 "?"。若是你的系統配置適當且本地化設置爲法語,那麼內部的 C 函數將告訴程序 "é" 也應該被認爲是一個字母。當在編譯正則表達式時使用 LOCALE 標誌會獲得用這些 C 函數來處理 "w 後的編譯對象;這會更慢,但也會象你但願的那樣能夠用 "w+ 來匹配法文文本。 7 8 U = UNICODE = sre_compile.SRE_FLAG_UNICODE # assume unicode locale 9 統一成unicode編碼 10 11 M = MULTILINE = sre_compile.SRE_FLAG_MULTILINE # make anchors look for newline 12 使用 "^" 只匹配字符串的開始,而 $ 則只匹配字符串的結尾和直接在換行前(若是有的話)的字符串結尾。當本標誌指定後, "^" 匹配字符串的開始和字符串中每行的開始。一樣的, $ 元字符匹配字符串結尾和字符串中每行的結尾(直接在每一個換行以前)。 13 14 S = DOTALL = sre_compile.SRE_FLAG_DOTALL # make dot match newline 15 使 "." 特殊字符徹底匹配任何字符,包括換行;沒有這個標誌, "." 匹配除了換行外的任何字符。 16 17 X = VERBOSE = sre_compile.SRE_FLAG_VERBOSE # ignore whitespace and comments 18 該標誌經過給予你更靈活的格式以便你將正則表達式寫得更易於理解。當該標誌被指定時,在 RE 字符串中的空白符被忽略,除非該空白符在字符類中或在反斜槓之後;這可讓你更清晰地組織和縮進 RE。它也能夠容許你將註釋寫入 RE,這些註釋會被引擎忽略;註釋用 "#"號 來標識,不過該符號不能在字符串或反斜槓之後。
re中的表示模式
模式 |
描述 |
^ |
匹配字符串的開頭 |
$ |
匹配字符串的末尾。 |
. |
匹配任意字符,除了換行符,當re.DOTALL標記被指定時,則能夠匹配包括換行符的任意字符。 |
[...] |
用來表示一組字符,單獨列出:[amk] 匹配 'a','m'或'k' |
[^...] |
不在[]中的字符:[^abc] 匹配除了a,b,c以外的字符。 |
re* |
匹配0個或多個的表達式。 |
re+ |
匹配1個或多個的表達式。 |
re? |
匹配0個或1個由前面的正則表達式定義的片斷,非貪婪方式 |
re{ n} |
|
re{ n,} |
精確匹配n個前面表達式。 |
re{ n, m} |
匹配 n 到 m 次由前面的正則表達式定義的片斷,貪婪方式 |
a| b |
匹配a或b |
(re) |
G匹配括號內的表達式,也表示一個組 |
(?imx) |
正則表達式包含三種可選標誌:i, m, 或 x 。隻影響括號中的區域。 |
(?-imx) |
正則表達式關閉 i, m, 或 x 可選標誌。隻影響括號中的區域。 |
(?: re) |
相似 (...), 可是不表示一個組 |
(?imx: re) |
在括號中使用i, m, 或 x 可選標誌 |
(?-imx: re) |
在括號中不使用i, m, 或 x 可選標誌 |
(?#...) |
註釋. |
(?= re) |
前向確定界定符。若是所含正則表達式,以 ... 表示,在當前位置成功匹配時成功,不然失敗。但一旦所含表達式已經嘗試,匹配引擎根本沒有提升;模式的剩餘部分還要嘗試界定符的右邊。 |
(?! re) |
前向否認界定符。與確定界定符相反;當所含表達式不能在字符串當前位置匹配時成功 |
(?> re) |
匹配的獨立模式,省去回溯。 |
\w |
匹配字母數字 |
\W |
匹配非字母數字 |
\s |
匹配任意空白字符,等價於 [\t\n\r\f]. |
\S |
匹配任意非空字符 |
\d |
匹配任意數字,等價於 [0-9]. |
\D |
匹配任意非數字 |
\A |
匹配字符串開始 |
\Z |
匹配字符串結束,若是是存在換行,只匹配到換行前的結束字符串。c |
\z |
匹配字符串結束 |
\G |
匹配最後匹配完成的位置。 |
\b |
匹配一個單詞邊界,也就是指單詞和空格間的位置。例如, 'er\b' 能夠匹配"never" 中的 'er',但不能匹配 "verb" 中的 'er'。 |
\B |
匹配非單詞邊界。'er\B' 能匹配 "verb" 中的 'er',但不能匹配 "never" 中的 'er'。 |
\n, \t, 等. |
匹配一個換行符。匹配一個製表符。等 |
\1...\9 |
匹配第n個分組的子表達式。 |
\10 |
匹配第n個分組的子表達式,若是它經匹配。不然指的是八進制字符碼的表達式。 |
演示代碼:
1 #!/usr/bin/env python 2 3 import re 4 5 #re.match從起始位置開始根據模型去字符串中匹配指定內容,匹配單個 6 #re .match(pattern, string, flags=0) 7 text = "111apple222pear" 8 f1 = re.match("\d+",text) 9 if f1:print(f1.group()) 10 else:print("無") 11 """運行一下試試,咱們能夠發現匹配到了111,因此咱們能夠肯定的是,match匹配的是從起始位置來去匹配, 12 起始位置匹配到了則正常,不然返回空 「\d+」表示匹配任意數字出現1次或者更屢次,若是把+號變成{1,2} 13 你就發現匹配的結果是11,這是由於{1,2}表示匹配一個或兩個""" 14 15 16 #re.search這個表示根據模式去匹配字符串中的匹配內容,也只匹配單個 17 #re.search(pattern, string, flags=0) 18 text = "aaa111apple222pear" 19 f1 = re.search("\d+",text) 20 if f1:print(f1.group()) 21 else:print("無") 22 #這個例子咱們發現,re.search把111匹配出來了因此他就是從整個字符串中匹配出模式符合的字符串,而且只匹配第一個 23 24 25 #group()與groups()的區別 26 text = "jnj111apple222pear" 27 f1 = re.search("([0-9]+)([a-z]+)",text) 28 if f1: 29 print(f1.group(0),f1.group(1),f1.group(2)) 30 print(f1.groups()) 31 else:print("無") 32 """看到結果清晰可見,re模塊匹配到後會將值傳入子組,group()默認不寫參數就返回匹配的整個值, 33 寫入參數就返回參數對應的值,而groups()則返回匹配到的值的元組""" 34 35 36 #匹配全部符合條件的值re.finadll(pattern, string, flags=0) 37 text = "jnj111apple222pear" 38 f1 = re.findall("([0-9]+)",text) 39 if f1:print(f1) 40 else:print("無") 41 """執行上面的例子,獲得的結果是個列表,列表中包含着全部符合條件的值([0-9]+)也能夠寫成(\d+)""" 42 43 44 #用於替換匹配條件的字符串re.sub(pattern, repl, string, count=0, flags=0) 45 text = "jnj111apple222pear" 46 f1 = re.sub("([a-z]+)",'A',text) 47 if f1:print(f1) 48 else:print("無") 49 #輸出的結果是全部的字母全變成大寫的A了相似於str.repalce 50 51 52 #re.split(pattern, string, maxsplit=0, flags=0) 53 content = "a1*b2c3*d4e5" 54 new_content = re.split('[\*]', content,2) 55 print (new_content) 56 #表示以*號做爲分割符保持在列表中相似於str.split 57 58 59 #將匹配規則賦予對象,這樣作的好處是能夠提高匹配的速度compile(pattern, flags=0) 60 import re 61 content = "a1b*2c3*d4e5" 62 aaa = re.compile('[\*]') 63 new_content = re.split(aaa, content) 64 print (new_content) 65 66 67 #將字符串中全部特殊正則表達式字符轉義escape(string) 68 import re 69 content = "a1b*2c3*d4e5" 70 ccc = re.escape(content) 71 print(ccc)
小練習
一、匹配出其中的年齡字段,字符串是:"name: aaa , age:22 , user:1112"
1 import re 2 str_in = 'name: aaa , age:22 , user:11121' 3 new_str_in = re.findall("[age]+\:\d{1,3}",str_in) 4 #表示age出現最低一次加上:號加上任意數字出現1到3次 5 print(new_str_in)
二、匹配出字符串中的全部網址,字符串是:"The url is www.aaa.com wwa.ccc.dsa www.cdsa.c"
1 import re 2 str_in = "The url is www.aaa.com wwa.ccc.dsa www.cdsa.c" 3 new_str_in = re.findall("www\.\S*\..{2,3}",str_in) 4 #以www加.加任意非空字符加任意字符出現次數爲2到3次 5 print(new_str_in)
三、算出括號中的值並進行替換,字符串是:"The name is xiaoyan The money I have (5+5),6-1'
1 import re 2 str_in = 'The name is xiaoyan The money I have (5+5),6-1' 3 new_str_in = re.findall("\(*\d+[\+]+\d+\)*",str_in)#匹配出括號中的內容 4 value = new_str_in[0].strip('(,)')#取出括號 5 n1, n2 = value.split('+')#以+做爲分割付 6 new_value = str(int(n1)+int(n2))#進行計算 7 aaa = str_in.replace(new_str_in[0],new_value)#進行替換 8 print(aaa)
官網網站提供的內置模塊文檔,點擊這裏
做者:北京小遠
出處:http://www.cnblogs.com/bj-xy/ 本文版權歸做者和博客園共有,歡迎轉載,但未經做者贊成必須在文章頁面明顯位置給出原文鏈接,不然保留追究法律責任的權利。