Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 优雅地停止线程_Python_Multithreading - Fatal编程技术网

Python 优雅地停止线程

Python 优雅地停止线程,python,multithreading,Python,Multithreading,我即将完成我的程序,我想在第一次发布之前修复这个错误 这就是我所说的错误: Exception ignored in: <module 'threading' from '/usr/local/Cellar/python/3.7.3/Frameworks/Python.framework/Versions/3.7/lib/python3.7/threading.py'> Traceback (most recent call last): File "/usr/local/Cel

我即将完成我的程序,我想在第一次发布之前修复这个错误

这就是我所说的错误:

Exception ignored in: <module 'threading' from '/usr/local/Cellar/python/3.7.3/Frameworks/Python.framework/Versions/3.7/lib/python3.7/threading.py'>
Traceback (most recent call last):
  File "/usr/local/Cellar/python/3.7.3/Frameworks/Python.framework/Versions/3.7/lib/python3.7/threading.py", line 1281, in _shutdown
    t.join()
  File "/usr/local/Cellar/python/3.7.3/Frameworks/Python.framework/Versions/3.7/lib/python3.7/threading.py", line 1032, in join
    self._wait_for_tstate_lock()
  File "/usr/local/Cellar/python/3.7.3/Frameworks/Python.framework/Versions/3.7/lib/python3.7/threading.py", line 1048, in _wait_for_tstate_lock
    elif lock.acquire(block, timeout):
KeyboardInterrupt
基本上就是这样。如何捕获此异常?我试了一下,除了已经试过了,但什么也没钓到

以下是MCVE:

import threading
import time

class MCVE:

    def __init__(self):

        self.list_1 = []

        self.init()

    def thread_1(self):

        while True:
            self.list_1.append('whatever')
            time.sleep(5)

    def thread_2(self):

        while True:
            for id, entry in enumerate(self.list_1):
                print('ID {} | entry: {}'.format(id, entry))
            time.sleep(10)

    def init(self):
        thread_1 = threading.Thread(target=self.thread_1)
        thread_2 = threading.Thread(target=self.thread_2)
        print('\nStarting threads...')
        print('- - - - - - - - - -\n')
        thread_1.start()
        thread_2.start()


def main():

    example = MCVE()

if __name__ == "__main__":
    main()

您没有提供可复制的示例,但这样可以成功停止程序,而不会引发未捕获的异常:

def foo(n):
    import time
    try:
        for i in range(n):
            time.sleep(i)
    except KeyboardInterrupt:
        print("Clean exit....")
        return

这可能有点晚,请尝试线程模块中的“Event()”方法,然后使用信号模块及其方法捕获信号。我将在下面留下一个链接,米格尔·格林伯格(Miguel Grinberg)对此做了简单而清晰的解释


链接:

什么是
新发布流
处理发布
?你的意思是使用一个名为
init
的方法来代替神奇的构造函数
\uuuuu init\uuuuuuu
?第一个线程从源代码流式发送帖子,第二个线程在帖子可用时立即处理。是的,
init
是从
\uuuuu init\uuuuu
调用的,我想让代码更干净一点。实际上这可能会有帮助:它只是一个函数。您可以调用
foo(5)
,在其运行时,点击Control+C,您将看到打印的消息OK。这对我不起作用。我不确定应该在何处使用此
except
,以成功捕获此错误。您可以首先使用
try/except
在每个级别包装每个可能的调用,以查看它是否有效。如果是这样的话,只需删除这些呼叫,直到找到正在工作的那一个。如果它不起作用,在你的情况下可能需要一些特殊的线程魔法。你能解释一下这个线程魔法吗?程序相当大,在try/except中包装每个调用有点乏味。找到了修复方法
thread.daemon=True
+
除了
main()
中的KeyboardInterrupt
外,此链接可以解决此问题。虽然此链接可以回答此问题,但最好在此处包含答案的基本部分,并提供链接供参考。如果链接页面发生更改,则仅链接的答案可能无效-
def foo(n):
    import time
    try:
        for i in range(n):
            time.sleep(i)
    except KeyboardInterrupt:
        print("Clean exit....")
        return