qthread.fined Signal IS不发出工人完成后发出
我有以下代码:
import time
from PyQt5.QtCore import QThread, QObject
from PyQt5.QtWidgets import QWidget, QApplication
class Worker(QObject):
def run(self):
time.sleep(1)
print("Worker is finished")
class MainWindow(QWidget):
def __init__(self):
super().__init__()
self.show()
self.thread = QThread()
self.worker = Worker()
self.worker.moveToThread(self.thread)
self.thread.started.connect(self.worker.run)
self.thread.finished.connect(self.on_thread_finished)
self.thread.start()
def on_thread_finished(self):
print("Thread finished")
self.thread.deleteLater()
if __name__ == "__main__":
app = QApplication([])
window = MainWindow()
app.exec_()
运行它,它显示窗口,打印工作者完成
,仅此而已。那很奇怪。恕我直言,工人完成后,线程也应完成,这意味着应调用on_thread_fined
方法,并且应打印thread完成
。但不是。为什么?
I have the following code:
import time
from PyQt5.QtCore import QThread, QObject
from PyQt5.QtWidgets import QWidget, QApplication
class Worker(QObject):
def run(self):
time.sleep(1)
print("Worker is finished")
class MainWindow(QWidget):
def __init__(self):
super().__init__()
self.show()
self.thread = QThread()
self.worker = Worker()
self.worker.moveToThread(self.thread)
self.thread.started.connect(self.worker.run)
self.thread.finished.connect(self.on_thread_finished)
self.thread.start()
def on_thread_finished(self):
print("Thread finished")
self.thread.deleteLater()
if __name__ == "__main__":
app = QApplication([])
window = MainWindow()
app.exec_()
Run it, it shows the window, prints Worker is finished
, nothing more. That's weird. IMHO when the worker is finished, the thread should be finished too, which means the on_thread_finished
method should be called and Thread finished
should be printed. But it wasn't. Why?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
当您使用
movetothread
而不是重新完成,该线程将启动自己的事件环,该循环将等到明确调用退出/退出
。仅在事件环停止后发出完成的
信号(和/或一次run
返回)。处理这种情况的通常方法是从工人发出自定义信号,并将其连接到线程的Quit
插槽。 (NB:跨线程信号插槽连接可以保证是线程安全的)。因此,您的示例将按照预期进行以下更改,可以按照预期工作:
When you use
moveToThread
instead of reimplementing QThread.run, the thread will start its own event-loop which will wait untilexit/quit
is explicitly called. Thefinished
signal is only emitted after the event-loop has stopped (and/or oncerun
returns). The usual way to handle this scenario is to emit a custom signal from the worker, and connect it to the thread'squit
slot. (NB: cross-thread signal-slot connections are guaranteed to be thread-safe).So your example will work as expected with the following changes:
这不是其工作原理。您的
Worker :: Run
方法通过常规signal> signal>/code>/
插槽>插槽
机制,将方法调用为插槽
Qthread
将继续按照正常方式处理事件。如果要终止
qthread
当wrorker :: Run
完成时,您需要告诉它要明确地做到这一点……非常“非常'',但它传达了这个想法。
Springs的一种更简单的替代方法是简单地使用
Qthread :: CusthRead()
,在这种情况下,您的worker :: Run
方法>方法>方法变为...That's not how it works. Your
Worker::run
method is being invoked as aslot
via the usualsignal
/slot
mechanism after which theQThread
will continue to process events as normal.If you want to terminate the
QThread
whenWorker::run
has completed you need to tell it to do so explicitly...Very 'inelegant' but it conveys the idea.
A simpler alternative that springs to mind would be to simply make use of
QThread::currentThread()
, in which case yourWorker::run
method becomes...