[PyQt] Segfault with QString
Phil Thompson
phil at riverbankcomputing.com
Fri Mar 21 11:04:59 GMT 2008
On Friday 21 March 2008, Filip Gruszczyński wrote:
> > It's practically impossible to help if you just post a code fragment. The
> > problem is almost certain to be in the bits of code you haven't posted.
> >
> > Try and come up with a simple but complete script that demonstrates the
> > problem so that other people can reproduce it.
>
> OK, I have created smaller script, that segfaults. Here it is:
>
> #!/usr/bin/python
>
> from PyQt4 import *
> from PyQt4.QtCore import *
> from PyQt4.QtGui import *
> import sys
>
> USE_SILENT = 1
> USE_REQUIRED = 2
>
> class NumericContent:
>
> def __init__(self, min = 0, max = 0):
> self.min = min
> self.max = max
>
> def getValues(self):
> return range(self.min, self.max + 1)
>
> class Element(QObject):
>
> def __init__(self, name, content = None, value = None):
> QObject.__init__(self)
> self.__name = name
> self.__content = content
> self.__value = value
>
> def getValue(self):
> return self.__value
>
> def setValue(self, value):
> self.__value = value
>
> def getName(self):
> return self.__name
>
> def hasContent(self):
> return self.__content != None
>
> def getContent(self):
> return self.__content
>
> def setContent(self, content):
> self.__content = content
>
> class Attribute(Element):
>
> def __init__(self, name, content):
> Element.__init__(self, name, content)
>
> def isFinal(self):
> return True
>
> def getValues(self):
> return self.getContent().getValues()
>
> def __repr__(self):
> return str(self.getName()) + " " + str(self.getValue()) + "\n"
>
> def display():
> print str(a.getValue())
>
> if __name__ == "__main__":
> app = QApplication(sys.argv)
> widget = QWidget()
> box = QComboBox()
> button = QPushButton("Button")
> layout = QHBoxLayout()
> layout.addWidget(box)
> layout.addWidget(button)
> widget.setLayout(layout)
> widget.show()
> a = Attribute('attr', NumericContent(1, 4))
> for i in a.getValues():
> box.addItem(QString(str(i)))
> box.connect(box, SIGNAL('currentIndexChanged(QString)'), a.setValue);
> box.emit(SIGNAL('currentIndexChanged(QString)'), box.currentText())
> box.connect(button, SIGNAL('clicked()'), display)
> sys.exit(app.exec_())
>
>
>
> To make it segfault, you just have to run it, change value in combo
> box, and push the button. If you don't change the the value in the
> combo box and push the button, it will correctly print the value onto
> the std out.
>
> Furthermore, if you change method
>
> def setValue(self, value):
> self.__value = value
>
> to
>
> def setValue(self, value):
> self.__value = str(value)
>
> it works perfectly fine. Can anyone explain me, what have I done wrong?
This is the same issue that came up the other day in the context of events.
The QString that value is wrapping is a temporary, so you either need to
convert it (as you do when calling str()) or copy it (by calling QString()).
Phil
More information about the PyQt
mailing list