如何捕获 Python 解释器的输出并显示在文本小部件中?

新手上路,请多包涵

我有一个使用 PyQt 编写的 Python 程序,旨在在 Windows 上运行。该程序进行了很多操作并打印了很多信息。但是因为我想冻结它并且不希望出现提示屏幕,所以我希望所有这些信息都出现在主应用程序中,比如 QTextEdit 中。我怎样才能使程序工作,以便它从解释器获取输出并同时在 textEdit 上显示它,就像在真正的解释器上一样?

原文由 jonathan.hepp 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 1k
2 个回答

我假设“解释器的输出”是指写入控制台或终端窗口的输出,例如 print() 产生的输出。

Python 生成的所有控制台输出都写入程序的输出流 sys.stdout (正常输出)和 sys.stderr (错误输出,例如异常回溯)。这些是类似文件的对象。

您可以用您自己的类文件对象替换这些流。您的所有自定义实现必须提供一个 write(text) 函数。通过提供您自己的实现,您可以将所有输出转发到您的小部件:

 class MyStream(object):
    def write(self, text):
        # Add text to a QTextEdit...

sys.stdout = MyStream()
sys.stderr = MyStream()

如果您需要重置这些流,它们仍然可用 sys.__stdout__sys.__stderr__

 sys.stdout = sys.__stdout__
sys.stderr = sys.__stderr__


更新

这是 PyQt4 的一些工作代码。首先定义一个流,报告使用 Qt 信号写入其中的数据:

 from PyQt4 import QtCore

class EmittingStream(QtCore.QObject):

    textWritten = QtCore.pyqtSignal(str)

    def write(self, text):
        self.textWritten.emit(str(text))

现在,在您的 GUI 中,将此流的实例安装到 sys.stdout 并将 textWritten 信号连接到将文本写入 QTextEdit 的插槽:

 # Within your main window class...

def __init__(self, parent=None, **kwargs):
    # ...

    # Install the custom output stream
    sys.stdout = EmittingStream(textWritten=self.normalOutputWritten)

def __del__(self):
    # Restore sys.stdout
    sys.stdout = sys.__stdout__

def normalOutputWritten(self, text):
    """Append text to the QTextEdit."""
    # Maybe QTextEdit.append() works as well, but this is how I do it:
    cursor = self.textEdit.textCursor()
    cursor.movePosition(QtGui.QTextCursor.End)
    cursor.insertText(text)
    self.textEdit.setTextCursor(cursor)
    self.textEdit.ensureCursorVisible()

原文由 Ferdinand Beyer 发布,翻译遵循 CC BY-SA 3.0 许可协议

不幸的是,该示例不适用于 PySide。它给出了以下错误:

 sys.stdout = EmittingStream(textWritten=self.write2Console)
AttributeError: 'textWritten()' is not a Qt property or a signal

我们需要进行以下更改才能与 PySide 一起使用:

 sys.stdout = EmittingStream()
self.connect(sys.stdout,QtCore.SIGNAL('textWritten(QString)'),self.write2Console)

原文由 TommyX 发布,翻译遵循 CC BY-SA 3.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题