3 回答
TA贡献1798条经验 获得超3个赞
需要记住的一件事是,每个线程都是单个代码流的顺序执行,从线程启动的函数开始。简单地在现有线程上运行某些内容没有多大意义,因为该线程已经在执行某些内容,并且这样做会破坏它的当前流程。
然而,线程之间的通信非常容易,并且可以实现线程的代码,使其仅从其他线程接收函数/事件来告诉它要做什么。这通常称为事件循环。
例如你的主线程可能看起来像这样
from queue import Queue
tasks = Queue()
def event_loop():
while True:
next_task = tasks.get()
print('Executing function {} on main thread'.format(next_task))
next_task()
在其他线程中,您可以通过简单地将函数添加到队列中来要求主线程运行该函数tasks:
def listenReply(self):
while self.SOCK_LISTENING:
fromNodeRED = self.nodeRED_sock.recv(1024).decode()
if fromNodeRED=="closeDoor":
tasks.put(door_closed)
TA贡献1804条经验 获得超3个赞
我自己使用 PyQt 的信号和插槽解决了这个问题。
class App(QWidget):
socketSignal = QtCore.pyqtSignal(object) #must be defined in class level
# BG THREAD
def listenReply(self):
while self.SOCK_LISTENING:
fromNodeRED = self.nodeRED_sock.recv(1024).decode()
print(fromNodeRED)
self.socketSignal.emit(fromNodeRED)
....主线程 init 中的某处:
self.socketSignal.connect(self.executeOnMain)
self.listenThread = Thread(target=self.listenReply, daemon=True)
self.SOCK_LISTENING = True
self.listenThread.start()
....
def executeOnMain(self, data):
if data=="closeDoor":
self.door_closed() # a method that changes the UI
对我来说效果很好。
TA贡献1824条经验 获得超8个赞
threading.Event()每当您收到来自 的“closeDoor”消息时,您都可以使用和设置它recv。
例如:
g_should_close_door = threading.Event()
def listenReply(self):
while self.SOCK_LISTENING:
fromNodeRED = self.nodeRED_sock.recv(1024).decode()
if fromNodeRED=="closeDoor":
g_should_close_door.set()
...
self.listenThread = Thread(target=self.listenReply, daemon=True)
self.SOCK_LISTENING = True
self.listenThread.start()
if g_should_close_door.is_set():
door_closed()
g_should_close_door.clear()
添加回答
举报