Debugging 薛定谔&x27;s Bug:PyQt QTimer事件仅在startTimer()上有断点时触发

Debugging 薛定谔&x27;s Bug:PyQt QTimer事件仅在startTimer()上有断点时触发,debugging,timer,pyqt4,Debugging,Timer,Pyqt4,这是一个奇迹般的bug:此代码的行为、打印输出和分支根据断点的位置而变化,而不是根据实际代码 从timerEvent()中的一个断点开始 timerEvent()中的此断点未触发 但是,当我在startTimer()上设置第二个断点,但不做任何其他更改时,timerEvent()中的断点现在被触发 #!/bin/python2 import sys from PyQt4.QtGui import QMainWindow, QApplication class SchrodingersWindo

这是一个奇迹般的bug:此代码的行为、打印输出和分支根据断点的位置而变化,而不是根据实际代码

timerEvent()
中的一个断点开始

timerEvent()
中的此断点未触发

但是,当我在
startTimer()
上设置第二个断点,但不做任何其他更改时,
timerEvent()
中的断点现在被触发

#!/bin/python2
import sys
from PyQt4.QtGui import QMainWindow, QApplication

class SchrodingersWindow(QMainWindow):
    def __init__(self, parent=None, flags=0):
        super(QMainWindow, self).__init__(parent)
        self.startTimer(0) # Try setting a breakpoint here

    def timerEvent(self, event):
        print "Something Timer Happened" # This never gets called unless the breakpoint is set on startTimer()

if __name__ == "__main__":
    app = QApplication(sys.argv)
    SchrodingersWindow()
    app.exec_()
薛定谔虫。在带wing调试器的pyqt中测试

使用多个版本的Wing debugger、两台计算机、Windows和Ubuntu进行测试


要测试这一点,您需要一个python调试器(我建议使用Wing)Python2.7和PyQt4,因为只要
SchrodingersWindow()
完成,就会删除保存窗口的对象,因为您从未存储引用。如果在
\uuuu init\uuuu
中进行调试,则对象正在创建过程中,
SchrodingersWindow()
尚未返回-尚未进行删除。比照

win = SchrodingersWindow()

每次执行
timerEvent

如果在
\uuuu init\uuuu
内设置断点,则在返回后,对象将保持活动状态。如果在调试器中“continue”(继续),将重复调用
timerEvent
,这表明事件循环必须已启动(即已到达
app.exec()
行)。因此,调试器确实改变了脚本的正常行为方式,因为窗口通常会在倒数第二行执行时被垃圾收集。但这里没有“bug”或“奇迹”——这只是调试器工作方式的副作用。(顺便说一下:我在Eric IDE中测试了大部分),我不习惯使用“垃圾收集”语言,也不知道调试器会影响垃圾收集。现在我知道了,我就能解决这个问题了!谢谢你的帮助,你很明白这一点