Python中threading的join和setDaemon的区别及用法
Python多線程編程時(shí)經(jīng)常會(huì)用到j(luò)oin()和setDaemon()方法,基本用法如下:
join([time]): 等待至線程中止。這阻塞調(diào)用線程直至線程的join() 方法被調(diào)用中止-正常退出或者拋出未處理的異常-或者是可選的超時(shí)發(fā)生。
setDaemon,將該線程標(biāo)記為守護(hù)線程或用戶線程
1、join ()方法:主線程A中,創(chuàng)建了子線程B,并且在主線程A中調(diào)用了B.join(),那么,主線程A會(huì)在調(diào)用的地方等待,直到子線程B完成操作后,才可以接著往下執(zhí)行,那么在調(diào)用這個(gè)線程時(shí)可以使用被調(diào)用線程的join方法。
原型:join([timeout]),里面的參數(shù)時(shí)可選的,代表線程運(yùn)行的最大時(shí)間,即如果超過(guò)這個(gè)時(shí)間,不管這個(gè)此線程有沒(méi)有執(zhí)行完畢都會(huì)被回收,然后主線程或函數(shù)都會(huì)接著執(zhí)行的。
import threading import timeclass MyThread(threading.Thread):def __init__(self, id):threading.Thread.__init__(self)self.id = iddef run(self):x = 0time.sleep(10)print(self.id)print('線程結(jié)束:'+str(time.time()))if __name__ == "__main__":t1 = MyThread(999)print('線程開(kāi)始:'+str(time.time()))t1.start()print('主線程打印開(kāi)始:'+str(time.time()))for i in range(5):print(i)time.sleep(2)print('主線程打印結(jié)束:' + str(time.time())) 線程開(kāi)始:1497534590.2784667 主線程打印開(kāi)始:1497534590.2794669 0 1 2 3 4 主線程打印結(jié)束:1497534592.279581 999 線程結(jié)束:1497534600.2800388從打印結(jié)果可知,線程t1 start后,主線程并沒(méi)有等線程t1運(yùn)行結(jié)束后再執(zhí)行,而是在線程執(zhí)行的同時(shí),執(zhí)行了后面的語(yǔ)句。
現(xiàn)在,把join()方法加到啟動(dòng)線程后面(其他代碼不變)
''' 遇到問(wèn)題沒(méi)人解答?小編創(chuàng)建了一個(gè)Python學(xué)習(xí)交流QQ群:778463939 尋找有志同道合的小伙伴,互幫互助,群里還有不錯(cuò)的視頻學(xué)習(xí)教程和PDF電子書(shū)! ''' import threading import timeclass MyThread(threading.Thread):def __init__(self, id):threading.Thread.__init__(self)self.id = iddef run(self):x = 0time.sleep(10)print(self.id)print('線程結(jié)束:'+str(time.time()))if __name__ == "__main__":t1 = MyThread(999)print('線程開(kāi)始:'+str(time.time()))t1.start()t1.join()print('主線程打印開(kāi)始:'+str(time.time()))for i in range(5):print(i)time.sleep(2)print('主線程打印結(jié)束:' + str(time.time())) 線程開(kāi)始:1497535176.5019968 999 線程結(jié)束:1497535186.5025687 主線程打印開(kāi)始:1497535186.5025687 0 1 2 3 4 主線程打印結(jié)束:1497535188.5026832線程t1 start后,主線程停在了join()方法處,等子線程t1結(jié)束后,主線程繼續(xù)執(zhí)行join后面的語(yǔ)句。
2、setDaemon()方法。主線程A中,創(chuàng)建了子線程B,并且在主線程A中調(diào)用了B.setDaemon(),這個(gè)的意思是,把主線程A設(shè)置為守護(hù)線程,這時(shí)候,要是主線程A執(zhí)行結(jié)束了,就不管子線程B是否完成,一并和主線程A退出.這就是setDaemon方法的含義,這基本和join是相反的。
此外,還有個(gè)要特別注意的:必須在start() 方法調(diào)用之前設(shè)置。
''' 遇到問(wèn)題沒(méi)人解答?小編創(chuàng)建了一個(gè)Python學(xué)習(xí)交流QQ群:778463939 尋找有志同道合的小伙伴,互幫互助,群里還有不錯(cuò)的視頻學(xué)習(xí)教程和PDF電子書(shū)! ''' import threading import timeclass MyThread(threading.Thread):def __init__(self, id):threading.Thread.__init__(self)self.id = iddef run(self):x = 0time.sleep(10)print(self.id)print("This is:" + self.getName()) # 獲取線程名稱print('線程結(jié)束:' + str(time.time()))if __name__ == "__main__":t1 = MyThread(999)print('線程開(kāi)始:'+str(time.time()))t1.setDaemon(True)t1.start()print('主線程打印開(kāi)始:'+str(time.time()))for i in range(5):print(i)time.sleep(2)print('主線程打印結(jié)束:' + str(time.time())) 線程開(kāi)始:1497536678.8509264 主線程打印開(kāi)始:1497536678.8509264 0 1 2 3 4 主線程打印結(jié)束:1497536680.8510408t1.setDaemon(True)的操作,將子線程設(shè)置為了守護(hù)線程。根據(jù)setDaemon()方法的含義,父線程打印內(nèi)容后便結(jié)束了,不管子線程是否執(zhí)行完畢了。
如果在線程啟動(dòng)前沒(méi)有加t1.setDaemon(True),輸出結(jié)果為:
線程開(kāi)始:1497536865.3215919 主線程打印開(kāi)始:1497536865.3215919 0 1 2 3 4 主線程打印結(jié)束:1497536867.3217063 999 This is:Thread-1 線程結(jié)束:1497536875.3221638程序運(yùn)行中,執(zhí)行一個(gè)主線程,如果主線程又創(chuàng)建一個(gè)子線程,主線程和子線程就分兵兩路,分別運(yùn)行,那么當(dāng)主線程完成想退出時(shí),會(huì)檢驗(yàn)子線程是否完成,如果子線程未完成,則主線程會(huì)等待子線程完成后再退出;
有時(shí)我們需要的是,子線程運(yùn)行完,才繼續(xù)運(yùn)行主線程,這時(shí)就可以用join方法(在線程啟動(dòng)后面);
但是有時(shí)候我們需要的是,只要主線程完成了,不管子線程是否完成,都要和主線程一起退出,這時(shí)就可以用setDaemon方法(在線程啟動(dòng)前面)。
總結(jié)
以上是生活随笔為你收集整理的Python中threading的join和setDaemon的区别及用法的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: python多线程用法及与单线程耗时比较
- 下一篇: 提高Python程序运行效率三种模式第一