import sys
from PyQt4 import QtGui
from PyQt4.QtCore import QObject, QBasicTimer
class Example(QObject):
def timerEvent(self, event):
print "timer event, timer Id:", event.timerId()
def main():
app = QtGui.QApplication(sys.argv)
ex = Example()
timer = QBasicTimer()
timer.start(500, ex)
print timer
timer = QBasicTimer()
timer.start(300, ex)
print timer
sys.exit(app.exec_())
#Run it
main()
使用这段代码,我希望看到2种不同的输出,它们在计时器ID上有所不同。但输出是:
<PyQt4.QtCore.QBasicTimer object at 0xb69b90>
<PyQt4.QtCore.QBasicTimer object at 0xb69c08>
timer event, timer Id: 33554433
timer event, timer Id: 33554433
timer event, timer Id: 33554433
timer event, timer Id: 33554433
timer event, timer Id: 33554433
timer event, timer Id: 33554433
同样奇怪的是,如果我更改第二个计时器的变量名称,如下所示:
timer = QBasicTimer()
timer.start(500, ex)
print timer
timer2 = QBasicTimer()
timer2.start(300, ex)
print timer2
然后我得到了预期的结果:
<PyQt4.QtCore.QBasicTimer object at 0x17b3b90>
<PyQt4.QtCore.QBasicTimer object at 0x17b3c08>
timer event, timer Id: 16777218
timer event, timer Id: 1
timer event, timer Id: 16777218
timer event, timer Id: 16777218
timer event, timer Id: 1
timer event, timer Id: 16777218
timer event, timer Id: 1
timer event, timer Id: 16777218
timer event, timer Id: 16777218
timer event, timer Id: 1
我正在尝试理解Python,这真让我感到困惑。是什么导致了这种行为?变量的名称如何改变程序?
答案 0 :(得分:1)
我不知道为什么你会认为这种行为很奇怪。事件的顺序就是这样:
ex = Example()
# timer(1) object is created
timer = QBasicTimer()
# ex object registers timer(1)
timer.start(500, ex)
print timer
# timer(2) object is created
# timer(1) object is destroyed
# timer(1) destructor unregisters timer(1)
timer = QBasicTimer()
# ex object registers timer(2)
timer.start(300, ex)
print timer
# event loop starts, 300ms later, timer(2) event is processed...
sys.exit(app.exec_())
所以这只是普通的python垃圾收集工作。创建具有相同名称的第二个对象将删除对第一个对象的唯一引用,该对象立即被垃圾收集。当然,第二个对象本身不会被垃圾收集,因为事件循环会阻止函数返回
如果您没有阅读QBasicTimer的文档,我想您可能已经考虑过这一行:
timer.start(500, ex)
会使ex
成为timer
的父级,从而使其保持活力。但要实现这一点,QBasicTimer
必须是QObject
的子类 - 它不是。{/ p>
QBasicTimer.start()
方法实际上与此相同:
def start(self, msec, obj):
self.stop()
if obj is not None:
self.id = obj.startImer(msec)