为何main()不加while True:sleep脚本就终止?daemon=False存疑
问题解答
首先,咱们得先厘清几个关键概念,还有你对代码中daemon属性的误解:
1. daemon 属性的真实作用
你对daemon=False的功能理解有偏差:
- 针对
multiprocessing.Process(子进程):
设置daemon=False的意思是父进程会等这个子进程完全结束后才退出,不是让子进程在父进程结束后还能存活。要是父进程意外终止,子进程会变成孤儿进程,被系统进程(比如init或systemd)接管,继续运行,这和daemon属性没关系。 - 针对
threading.Thread(线程):
设置daemon=False意味着进程会等这个线程跑完才终止。只要进程里还有至少一个非守护线程在运行,进程就不会退出。
2. 为什么你看到Method A里线程会终止?
按照Python的线程规则,子进程的main()函数执行完(主线程结束)后,子进程应该等待所有非守护线程(你的thread1和thread2)完成才会终止——而这两个线程是无限循环,所以子进程应该一直跑,父进程也会因为等子进程而保持存活,脚本不该终止。
但你看到线程终止,大概率是下面某个原因:
- IDE/终端的输出缓冲或行为问题:
比如有些IDE里,主进程主线程结束后,会把子进程的输出隐藏起来,让你误以为线程停了;或者终端的输出缓冲导致你看不到后续的打印内容。你可以试试在终端里直接运行脚本,看看还会不会有这个问题。 - Windows系统
spawn启动方式的特殊情况:
Windows上multiprocessing默认用spawn创建子进程,子进程会重新导入整个模块。如果代码里有隐式的依赖问题(比如全局变量初始化),可能导致线程没法正常启动,但你的代码看起来没这个问题。 - 误解了脚本的终止状态:
运行Method A时,主进程会等子进程,所以子进程一直跑的话,主进程也会保持存活,脚本不会终止。你看到的“脚本终止”可能是主进程和子进程都停了,这种情况大概率是测试环境的问题,不是代码逻辑的问题。
3. 为什么加while True: time.sleep(1)后线程能存活?
在main()里加这个循环后,子进程的主线程会一直处于运行状态(不会结束),子进程自然不会进入退出流程,线程就能正常跑了。这本质上是让子进程的主线程保持活跃,不是依赖线程的daemon属性。
结论
你的代码逻辑本身是对的:只要thread1和thread2是非守护线程且无限循环,子进程就应该一直运行。你看到的异常现象大概率是测试环境或输出缓冲导致的。建议你在终端直接运行脚本,或者让子进程的线程输出到日志文件,验证线程是不是真的终止了。
内容的提问来源于stack exchange,提问作者duarte
相关产品推荐
相关产品推荐

