如何在中断读取Arduino的Python代码时自动关闭serial连接?
解决Python脚本中断时自动关闭Arduino串口的问题
这个问题我碰到过好多次——手动中断串口读取脚本后,串口资源没释放,导致下次启动脚本直接报错端口被占用。下面分享两种可靠的方法,让你不用手动输入ser.close(),中断时就能自动关闭串口:
方法1:用try-except-finally块兜底
finally 块的特性是无论是否触发异常,里面的代码都会执行,刚好适合用来清理串口、文件这类资源。
示例代码:
import serial # 初始化串口和输出文件,替换成你的实际端口和波特率 ser = serial.Serial('COM3', 9600) output_file = open('arduino_data.txt', 'a') try: # 主循环:持续读取串口数据并写入文件 while True: raw_data = ser.readline().decode('utf-8').strip() if raw_data: print(f"收到数据:{raw_data}") output_file.write(raw_data + '\n') output_file.flush() # 强制刷新缓存,避免数据滞留 except KeyboardInterrupt: # 捕获Ctrl+C触发的中断信号,给个提示 print("\n用户中断了脚本执行") finally: # 不管有没有异常,最后都要关闭资源 ser.close() output_file.close() print("串口和文件已成功关闭")
当你按下Ctrl+C时,except块会先捕获中断,随后finally块自动执行关闭操作,完全不用手动干预。
方法2:用上下文管理器(推荐写法)
Python的serial.Serial类支持上下文管理器(也就是with语句),这是更简洁的资源管理方式。只要在with块里操作串口,不管是正常退出还是异常中断,Python都会自动帮你调用close()方法。
示例代码:
import serial # 用with语句同时管理串口和文件资源 with serial.Serial('COM3', 9600) as ser, open('arduino_data.txt', 'a') as output_file: try: while True: raw_data = ser.readline().decode('utf-8').strip() if raw_data: print(f"收到数据:{raw_data}") output_file.write(raw_data + '\n') output_file.flush() except KeyboardInterrupt: print("\n脚本被中断,串口和文件已自动关闭")
这种写法不需要手动写关闭代码,Python帮你兜底,代码更干净易读,是处理资源释放的最佳实践。
额外小提示
- 务必保证串口的端口号、波特率和Arduino代码里的设置完全一致,不然会出现读取异常;
output_file.flush()很重要,能避免数据留在内存缓存里,确保实时写入文件;- 如果脚本可能遇到其他异常(比如串口读取失败),可以额外添加
except块捕获,但KeyboardInterrupt是处理Ctrl+C中断的核心。
内容的提问来源于stack exchange,提问作者SuperCiocia
相关产品推荐
相关产品推荐

