我正在开发一个使用套接字进行通信的接口(interface)。我需要使用线程才能同时接收和发送数据。
下面的代码是连续发送数据的模块的简化版本。
我的问题是,在开发过程中,我需要频繁地启动和停止,但线程似乎无法像普通脚本那样停止应用程序。该进程需要在进程管理器中终止才能重新启动。
我感觉我误解了一些东西。
我环顾四周,但看到大量不一致的答案,我尝试实现这些答案却无济于事。我尝试过处理 KeyboardInterrupt 异常,但不起作用。
有什么想法吗?
import socket
import sys
import threading
running = True
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server_address = ('localhost', 50000)
print ('connecting to %s port %s' % server_address)
sock.connect(server_address)
class TelemetryPacket:
state = "N/A"
def __init__(self, stringvalue):
self.state = stringvalue
def serialise(self):
return "%s" % (self.state)
def send(running):
try:
while (running):
telemetry = TelemetryPacket(0).serialise()
sock.sendto(telemetry.encode('utf-8'), server_address)
except KeyboardInterrupt:
print ("threads successfully closed")
running = False
def recv(running):
try:
while (running):
data = sock.recv(1)
if (data):
print("data received: %s" % data)
except KeyboardInterrupt:
print ("threads successfully closed")
running = False
a = threading.Thread(target=send, args=(running,))
a.start()
b = threading.Thread(target=recv, args=(running,))
b.start()
最佳答案
您应该在主线程中捕获键盘中断,然后向子线程发送信号以退出并重新加入主线程。您还应该使用更线程安全的信号来发送信号,例如基本的 threading.Event()
,因此:
import threading
import time
exit_signal = threading.Event() # your global exit signal
def send():
while not exit_signal.is_set():
pass # whatever you need
def recv():
while not exit_signal.is_set():
pass # whatever you need
# create the threads
a = threading.Thread(target=send)
b = threading.Thread(target=recv)
# start the threads
a.start()
b.start()
# create a main thread loop
try:
while not exit_signal.is_set(): # enable children threads to exit the main thread, too
time.sleep(0.1) # let it breathe a little
except KeyboardInterrupt: # on keyboard interrupt...
exit_signal.set() # send signal to all listening threads
# join back the threads
a.join()
b.join()
# and you're done...
关于python - 键盘中断、套接字和线程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47847392/