如何使用 PyQt 在 python 应用程序中处理 Ctrl+C?
Posted
技术标签:
【中文标题】如何使用 PyQt 在 python 应用程序中处理 Ctrl+C?【英文标题】:How to handle Ctrl+C in python app with PyQt? 【发布时间】:2017-03-15 15:28:10 【问题描述】:我有一个基于 PyQt4 的 python 2.7 应用程序。我需要在特定的处理程序中处理 Ctrl+C (KeyboardInterrupt
, SIGINT
, 2)。我看到通过按 Ctrl+C 创建的异常未在 try-except
块中捕获,并且未在处理函数中看到,由 signal
库注册。 Ctrl+C 什么都不做!
我尝试在没有 PyQt 的情况下做同样的事情 - signal
效果很好。
用于测试的代码不使用任何 PyQt API,因此我在这两种情况下都可以使用它进行检查。
【问题讨论】:
【参考方案1】:CTRL+C 导致向进程发送信号。 Python 捕获信号,并设置一个全局变量,例如 CTRL_C_PRESSED = True。然后,每当 Python 解释器开始执行新的操作码时,它都会看到变量集并引发 KeybordInterrupt。
这意味着 CTRL+C 仅在 Python 解释器正在旋转时才起作用。如果解释器正在执行一个用 C 编写的扩展模块,该模块执行一个长时间运行的操作,CTRL+C 不会中断它,除非它显式地与 Python “合作”。例如:time.sleep() 理论上是一个阻塞操作,但该函数的实现与 Python 解释器“合作”以使 CTRL+C 工作。
这都是设计使然:CTRL+C 是为了“彻底中止”;这就是为什么它被 Python 变成异常的原因(以便在堆栈展开期间执行清理),并且扩展模块对它的支持有点“选择加入”。如果你想完全中止进程,不给它清理的机会,你可以使用 CTRL+。
当 Python 调用 QApplication::exec()(C++ 函数)时,Qt 不知道如何与 Python “合作”以实现 CTRL+C,这就是它不起作用的原因。我认为没有“让它发挥作用”的好方法;您可能想看看是否可以通过全局事件过滤器来处理它。 — 乔瓦尼·巴霍
将这个添加到主程序解决了这个问题。
import signal
signal.signal(signal.SIGINT, signal.SIG_DFL)
我不确定这与解释有什么关系。
【讨论】:
好的,它允许我在不处理的情况下杀死我的程序。 Ctrl+C可以处理吗?import signal
import sys
def signal_term_handler(signal, frame):
print 'got SIGTERM'
sys.exit(0)
signal.signal(signal.SIGTERM, signal_term_handler)
以上是关于如何使用 PyQt 在 python 应用程序中处理 Ctrl+C?的主要内容,如果未能解决你的问题,请参考以下文章
如何在 PyQt4 中使用 QtGui 来收集 Python 程序的输入变量?
如何使 Python PyQT 程序无法在 Windows 中打开命令行
使用 Anaconda Python 的 PyQt Windows 安装程序 - 未找到 PyQt4;如何进行故障排除?