Python 的 daemon 線程的精講---通透

關於 Python 中的 daemon 的設置說明:
https://www.cnblogs.com/xfiver/p/5189732.html

Daemons are only useful when the main program is running,
and it’s okay to kill them off once the other non-daemon threads have exited.
Without daemon threads, we have to keep track of them, and tell them to exit, before our program can completely quit.
By setting them as daemon threads,
we can let them run and forget about them, and when our program quits, any daemon threads are killed automatically.
Daemon線程當且僅當主線程運行時有效,當其他非Daemon線程結束時可自動殺死所有Daemon線程。
如果沒有Daemon線程的定義,則必須手動的跟蹤這些線程,在程序結束前手動結束這些線程。
通過設置線程爲Daemon線程,則可以放任它們運行,並遺忘它們,當主程序結束時這些Daemon線程將自動被殺死。

Python主程序當且僅當不存在 非Daemon 線程存活時退出。
即:主程序等待所有非Daemon線程結束後才退出,且退出時會自動結束(很粗魯的結束)所有Daemon線程。

亦理解爲:Daemon設置爲子線程是否隨主線程一起結束,默認爲False。如果要隨主線程一起結束需要設置爲True。

import time, threading
import datetime
def run_thread(n , b):
    print '{0}: In run_thread: Current thead is {1}'.format(datetime.datetime.now(), threading.current_thread())
    print '{0}: n = {1}'.format(datetime.datetime.now(), n)
    time.sleep(5)
    print '{0}: b = {1}'.format(datetime.datetime.now(), b)
print '{0}: Current thead is {1}'.format(datetime.datetime.now(),threading.current_thread())

# Case1: 在主進程中調用 t1.join() 時,主進程會阻塞在該處並且等待子線程結束
# root@robert-Ubuntu:/media/sf_WorkSpace/HelloNG/src/testcode# python threading_daemon.py
# 2020-06-30 11:16:07.808415: Current thead is <_MainThread(MainThread, started 140504184133376)>
# 2020-06-30 11:16:07.808678: t1.daemon = False
# 2020-06-30 11:16:07.809016: In run_thread: Current thead is <Thread(first thread with customized name, started 140504165930752)>
# 2020-06-30 11:16:07.809145: n = 5
# 2020-06-30 11:16:12.814438: b = 3
# 2020-06-30 11:16:12.814633: end of the process!!!
# root@robert-Ubuntu:/media/sf_WorkSpace/HelloNG/src/testcode#
# t1 = threading.Thread(target=run_thread, args=(5,3), name = 'first thread with customized name')
# print '{0}: t1.daemon = {1}'.format(datetime.datetime.now(), t1.daemon)
# t1.start()
# t1.join()
# print '{0}: end of the process!!!'.format(datetime.datetime.now())
#
# Case2: 當主進程 沒有 t1.join() 且運行到結束的時候: 如果子線程的 daemon 值爲 False,則依然會等待子線程結束
# Python主程序當且僅當不存在 非Daemon 線程存活時退出。
# 即:主程序等待所有非Daemon線程結束後才退出,且退出時會自動結束(很粗魯的結束)所有Daemon線程。
# 亦理解爲:Daemon設置爲子線程是否隨主線程一起結束,默認爲False。如果要隨主線程一起結束需要設置爲True。
# from: https://www.cnblogs.com/xfiver/p/5189732.html
# root@robert-Ubuntu:/media/sf_WorkSpace/HelloNG/src/testcode# python threading_daemon.py
# 2020-06-30 11:16:54.185968: Current thead is <_MainThread(MainThread, started 139965824337664)>
# 2020-06-30 11:16:54.186078: t1.daemon = False
# 2020-06-30 11:16:54.186558: In run_thread: Current thead is <Thread(first thread with customized name, started 139965806135040)>
#  2020-06-30 11:16:54.186912: n = 5
# 2020-06-30 11:16:54.186664: end of the process!!!
# 2020-06-30 11:16:59.194845: b = 3
# root@robert-Ubuntu:/media/sf_WorkSpace/HelloNG/src/testcode#
#
t1 = threading.Thread(target=run_thread, args=(5,3), name = 'first thread with customized name')
print '{0}: t1.daemon = {1}'.format(datetime.datetime.now(), t1.daemon)
t1.start()
print '{0}: end of the process!!!'.format(datetime.datetime.now())

# Case 3: 當主進程 沒有 t1.join() 且運行到結束的時候: 如果子線程的 daemon 值爲 True,則主進程在自己退出的時候會粗暴的結束子線程
#         可以通過 ps -eLf | grep process_name 來驗證“主進程在自己退出的時候會粗暴的結束子線程”而不是放任不管它
# root@robert-Ubuntu:/media/sf_WorkSpace/HelloNG/src/testcode# python threading_daemon.py
# 2020-06-30 11:18:05.438126: Current thead is <_MainThread(MainThread, started 139762719913728)>
# 2020-06-30 11:18:05.438258: t1.daemon = True
# 2020-06-30 11:18:05.438677: In run_thread: Current thead is <Thread(first thread with customized name, started daemon 139762701711104)>
#  2020-06-30 11:18:05.439043: n = 5
# 2020-06-30 11:18:05.438808: end of the process!!!
# root@robert-Ubuntu:/media/sf_WorkSpace/HelloNG/src/testcode#
#
# t1 = threading.Thread(target=run_thread, args=(5,3), name = 'first thread with customized name')
# t1.setDaemon(True)
# print '{0}: t1.daemon = {1}'.format(datetime.datetime.now(), t1.daemon)
# t1.start()
# print '{0}: end of the process!!!'.format(datetime.datetime.now())
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章