当前位置: 首页 > 面试题库 >

使我的PyQt应用程序从控制台中退出时(Ctrl-C),退出的正确方法是什么?

巫新知
2023-03-14
问题内容

使我的PyQt应用程序从控制台中退出时(Ctrl-C),退出的正确方法是什么?

当前(我在处理unix信号方面没有做任何特别的事情),我的PyQt应用程序忽略了SIGINT(Ctrl +
C)。我希望它表现良好并在被杀死时退出。我该怎么办?


问题答案:

17.4。signal —设置异步事件的处理程序

尽管就Python用户而言,Python信号处理程序是异步调用的,但它们只能出现在Python解释器的“原子”指令之间。这意味着纯粹在C语言中执行的长计算期间到达的信号(例如,大文本正文中的正则表达式匹配)可能会延迟任意时间。

这意味着在Qt事件循环运行时,Python无法处理信号。仅当Python解释器运行时(退出QApplication或从Qt调用Python函数时),才会调用信号处理程序。

一种解决方案是使用QTimer让解释器不时运行。

请注意,在下面的代码中,如果没有打开的窗口,则应用程序将在消息框后退出,而不考虑用户的选择,因为QApplication.quitOnLastWindowClosed()==
True。可以更改此行为。

import signal
import sys

from PyQt4.QtCore import QTimer
from PyQt4.QtGui import QApplication, QMessageBox

# Your code here

def sigint_handler(*args):
    """Handler for the SIGINT signal."""
    sys.stderr.write('\r')
    if QMessageBox.question(None, '', "Are you sure you want to quit?",
                            QMessageBox.Yes | QMessageBox.No,
                            QMessageBox.No) == QMessageBox.Yes:
        QApplication.quit()

if __name__ == "__main__":
    signal.signal(signal.SIGINT, sigint_handler)
    app = QApplication(sys.argv)
    timer = QTimer()
    timer.start(500)  # You may change this if you wish.
    timer.timeout.connect(lambda: None)  # Let the interpreter run each 500 ms.
    # Your code here.
    sys.exit(app.exec_())

如LinearOrbit所指出的,另一个可能的解决方案是signal.signal(signal.SIGINT, signal.SIG_DFL),但是它不允许自定义处理程序。



 类似资料:
  • Ctrl-C/SIGTERM/SIGINT似乎被tkinter忽略。通常情况下,它可以通过回调再次捕获。这似乎不起作用,所以我想我应该在另一个线程中运行tkinter,因为它的main循环()是一个无限循环和块。实际上,我也想这样做,以便在一个单独的线程中阅读stdin。即使在此之后,Ctrl-C仍然不会处理,直到我关闭窗口。这是我的MWE: 结果: 运行应用程序 终端中的Ctrl-C(什么都没发

  • **更新--问题不是文件编写器没有关闭,而是错误地终止了Java应用程序。我已经更新了问题。 下面的类启动JAVAFX web视图,并将一些java对象公开给web视图的HTML。 实际上,WebEngine.executescrit(“init”)在我们的前端执行一些初始化。然后,在webview上执行的javascript上,在用户交互上,我们调用我们的FileSystemBridge的wri

  • 本文向大家介绍Elixir退出IEX控制台,包括了Elixir退出IEX控制台的使用技巧和注意事项,需要的朋友参考一下 示例 使用Ctrl + C,Ctrl + C退出 使用Ctrl+ \立即退出

  • 本文向大家介绍python子线程退出及线程退出控制的代码,包括了python子线程退出及线程退出控制的代码的使用技巧和注意事项,需要的朋友参考一下 下面通过代码给大家介绍python子线程退出问题,具体内容如下所示: 跑起来是没有问题的,但是使用ctrl + c中断的时候出问题了,主线程退出了,但子线程仍然运行。 于是在主线程增加了信号处理的代码,收到sigint时改变子线程循环条件 这样ctrl

  • 问题内容: 在Go中,设置流程退出代码的正确方法是什么? 我尝试将主要功能更改为 但这会导致错误 好的,所以有,但是这会立即中止该过程并且不会干净退出(例如,不执行任何递延操作)。 我还发现它将退出进程并将状态代码设置为非零,这可能是最好的方法,尽管它会将堆栈跟踪信息转储到控制台。 设置退出代码的正确方法是什么? 问题答案: 使最后一个延迟函数执行。延迟函数在周围函数返回之前立即执行,以相反的顺序

  • 问题内容: 用代码退出Java应用程序的最佳方法是什么? 问题答案: 您可以用于此目的。 根据oracle的Java 8文档: 终止当前正在运行的Java虚拟机。参数用作状态码;按照惯例, 非零状态代码表示异常终止 。 此方法在类Runtime中调用exit方法。此方法永远不会正常返回。 该调用实际上等效于该调用: