Python多線程threading模塊用法實(shí)例分析
本文實(shí)例講述了Python多線程threading模塊用法。分享給大家供大家參考,具體如下:
多線程 - threading
python的thread模塊是比較底層的模塊,python的threading模塊對(duì)thread做了一些包裝,可以更加方便的被使用。
1. 使用threading模塊
單線程執(zhí)行
#coding=utf-8 import time def saySorry(): print('跑一圈') time.sleep(1) if __name__ == "__main__": for i in range(5): saySorry()
運(yùn)行結(jié)果:
跑一圈
跑一圈
跑一圈
跑一圈
跑一圈
多線程執(zhí)行
#coding=utf-8 import threading import time def saySorry(): print('跑一圈') time.sleep(1) if __name__ == "__main__": for i in range(5): t = threading.Thread(target=saySorry) t.start()#啟動(dòng)線程
運(yùn)行結(jié)果:
跑一圈
跑一圈
跑一圈
跑一圈
跑一圈
說明
①. 通過運(yùn)行可以明顯看出使用多線程并發(fā)操作,花費(fèi)時(shí)間要短很多。
②. 創(chuàng)建好的線程,需要調(diào)用 start()
方法來(lái)啟動(dòng)
2. 主線程會(huì)等待所有的子線程結(jié)束后才結(jié)束
#coding=utf-8 import threading from time import sleep,ctime,time def run(): for i in range(3): print('在跑步...%d'%i) sleep(1) def sing(): for i in range(3): print('在唱歌...%d'%i) sleep(1) if __name__ == "__main__": print('------start------' + ctime()) t1 = threading.Thread(target=run) t2 = threading.Thread(target=sing) t1.start()#啟動(dòng)線程 t2.start() # sleep(5)# 屏蔽此行代碼,試試看,程序是否會(huì)立即結(jié)束? print('------stop------' + ctime())
運(yùn)行結(jié)果:
------start------Thu Aug 24 13:38:28 2017
在跑步...0
------stop------Thu Aug 24 13:38:28 2017
在唱歌...0
在跑步...1
在唱歌...1
在跑步...2
在唱歌...2
3. 查看線程數(shù)量
#coding=utf-8 import threading from time import sleep,ctime,time def run(): for i in range(3): print('在跑步...%d'%i) sleep(1) def sing(): for i in range(3): print('在唱歌...%d'%i) sleep(1) if __name__ == "__main__": print('------start------' + ctime()) t1 = threading.Thread(target=run) t2 = threading.Thread(target=sing) t1.start()#啟動(dòng)線程 t2.start() while True: length = len(threading.enumerate()) print('當(dāng)前運(yùn)行的線程數(shù)為:' , length , ctime()) if length <= 1: break # sleep(5)# 屏蔽此行代碼,試試看,程序是否會(huì)立即結(jié)束? print('------stop------' + ctime())
運(yùn)行結(jié)果:
由于數(shù)量龐大,在此不展示。。。。。。
4.線程執(zhí)行代碼的封裝 - threading.Thread子類
#coding=utf-8 import threading import time class MyThread(threading.Thread): def run(self): for i in range(3): time.sleep(1) msg = 'i am '+self.name+'@'+str(i) #name屬性中保存的是當(dāng)前線程的名字 print(msg) if __name__ == "__main__": t = MyThread() t.start()
運(yùn)行結(jié)果:
i am Thread-1@0
i am Thread-1@1
i am Thread-1@2
說明:
python的threading.Thread
類有一個(gè)run方法,用于定義線程的功能函數(shù),可以在自己的線程類中覆蓋該方法。在創(chuàng)建自己的線程實(shí)例后,通過Thread類的start()
方法,可以啟動(dòng)該線程,交給python虛擬機(jī)進(jìn)行調(diào)度,當(dāng)該線程獲得執(zhí)行的機(jī)會(huì)時(shí),就會(huì)調(diào)用run方法執(zhí)行線程。
5.線程的執(zhí)行順序
#coding=utf-8 import threading import time class MyThread(threading.Thread): def run(self): for i in range(3): time.sleep(1) msg = 'i am '+self.name+'@'+str(i) #name屬性中保存的是當(dāng)前線程的名字 print(msg) def test(): for i in range(5): t = MyThread() t.start() if __name__ == "__main__": test()
運(yùn)行結(jié)果:
i am Thread-1@0
i am Thread-2@0
i am Thread-3@0
i am Thread-4@0
i am Thread-5@0
i am Thread-1@1
i am Thread-2@1
i am Thread-3@1
i am Thread-4@1
i am Thread-5@1
i am Thread-1@2
i am Thread-2@2
i am Thread-3@2
i am Thread-4@2
i am Thread-5@2
說明:
(運(yùn)行的結(jié)果可能不一樣,但是大體是一致的)
從代碼的執(zhí)行結(jié)果我們可以看出,多線程程序的執(zhí)行順序是不確定的。當(dāng)執(zhí)行到sleep語(yǔ)句時(shí),線程將被阻塞(Blocked),到sleep結(jié)束后,線程進(jìn)入就緒(Runnable)狀態(tài),等待調(diào)度。而線程調(diào)度將自行選擇一個(gè)線程執(zhí)行。上面的代碼中只能保證每個(gè)線程都運(yùn)行完整個(gè)run函數(shù),但是線程的啟動(dòng)順序、
run函數(shù)中每次循環(huán)的執(zhí)行順序都不能確定。
總結(jié)
1. 每個(gè)線程一定會(huì)有一個(gè)名字,盡管上面的例子中沒有指定線程對(duì)象的name,但是python會(huì)自動(dòng)為線程指定一個(gè)名字。
2. 當(dāng)線程的run()方法結(jié)束時(shí)該線程完成。
3. 無(wú)法控制線程調(diào)度程序,但可以通過別的方式來(lái)影響線程調(diào)度的方式。
4. 線程的幾種狀態(tài)
多線程-共享全局變量
#coding=utf-8 import threading import time g_num = 100 def work1(): global g_num for i in range(3): g_num+=1 print('work1 --- num = %d'%g_num) def work2(): global g_num print('work2 --- num = %d'%g_num) if __name__ == "__main__": print('---start------g_num = %d'%g_num) t1 = threading.Thread(target=work1) t1.start() # 延時(shí)一會(huì),保證t1線程中的事情做完 time.sleep(1) t2 = threading.Thread(target=work2) t2.start()
運(yùn)行結(jié)果:
---start------g_num = 100
work1 --- num = 103
work2 --- num = 103
更多關(guān)于Python相關(guān)內(nèi)容感興趣的讀者可查看本站專題:《Python進(jìn)程與線程操作技巧總結(jié)》、《Python數(shù)據(jù)結(jié)構(gòu)與算法教程》、《Python函數(shù)使用技巧總結(jié)》、《Python字符串操作技巧匯總》、《Python入門與進(jìn)階經(jīng)典教程》、《Python+MySQL數(shù)據(jù)庫(kù)程序設(shè)計(jì)入門教程》及《Python常見數(shù)據(jù)庫(kù)操作技巧匯總》
希望本文所述對(duì)大家Python程序設(shè)計(jì)有所幫助。
相關(guān)文章
python爬蟲將js轉(zhuǎn)化成json實(shí)現(xiàn)示例
這篇文章主要為大家介紹了python爬蟲將js轉(zhuǎn)化成json實(shí)現(xiàn)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-05-05python GUI庫(kù)圖形界面開發(fā)之PyQt5信號(hào)與槽基本操作
這篇文章主要介紹了python GUI庫(kù)圖形界面開發(fā)之PyQt5信號(hào)與槽基本操作,需要的朋友可以參考下2020-02-02Python猴子補(bǔ)丁知識(shí)點(diǎn)總結(jié)
在本篇文章里小編給大家分享的是關(guān)于Python猴子補(bǔ)丁知識(shí)點(diǎn)總結(jié),需要的朋友們學(xué)習(xí)下。2020-01-01Python爬蟲入門有哪些基礎(chǔ)知識(shí)點(diǎn)
在本篇文章中小編給大家整理的是關(guān)于Python爬蟲入門基礎(chǔ)知識(shí)點(diǎn)整理,有興趣的朋友們可以跟著學(xué)習(xí)下。2020-06-06Python web開發(fā)之用Tornado框架制作簡(jiǎn)易表白墻網(wǎng)站
這篇文章將用Python做Web開發(fā)。在Python當(dāng)中,WEB開發(fā)框架主要有三個(gè),本文將利用Tornado框架做一個(gè)簡(jiǎn)單的表白墻網(wǎng)站,感興趣的可以了解一下2022-02-02python偏函數(shù)的實(shí)例用法總結(jié)
在本篇文章里小編給大家整理的是一篇關(guān)于python偏函數(shù)的實(shí)例用法總結(jié)內(nèi)容,有興趣的朋友們可以跟著學(xué)習(xí)參考下。2021-07-07