Wenn Sie mit PySide ein baumförmiges Modell erstellen, möchten Sie möglicherweise nacheinander auf alle Elemente zugreifen.
Wenn Sie QTreeWidget verwenden, können Sie mit QTreeWidgetItemIterator nacheinander darauf zugreifen. (Da es sich um eine Bibliothek für C ++ handelt, ist die Verwendung mit Python etwas unpraktisch.) Ich habe es erstellt, weil ich den Iterator für QStandardItemModel und mein eigenes Modell verwenden möchte.
Der Code ist python2, aber da xrange nicht verwendet wird, funktioniert er wie in python3.
#! usr/bin/python
# -*- coding: utf-8 -*-
from __future__ import unicode_literals, print_function, absolute_import
from PySide.QtCore import *
from PySide.QtGui import *
def model_iter(model, parent_index=QModelIndex(), col_iter=True):
"""Modelliterator
:rtype: generator(QModelIndex)
:type col_iter: bool
:type parent_index: QModelIndex
:type model: QAbstractItemModel
"""
index = model.index(0, 0, parent_index)
while True:
if col_iter:
for col in range(0, model.columnCount(parent_index)):
yield index.sibling(index.row(), col)
else:
yield index
if model.rowCount(index) > 0:
for _ in model_iter(model, index, col_iter):
yield _
index = index.sibling(index.row() + 1, index.column())
if not index.isValid():
break
Es ist einfach zu bedienen, übergeben Sie einfach das Modell und es wird der Iterator zurückgegeben.
tree_model = QStandardItemModel()
item = QStandardItem("A")
item.appendRow(QStandardItem("A-1"))
item.appendRow(QStandardItem("A-2"))
tree_model.appendRow(item)
item = QStandardItem("B")
item.appendRow(QStandardItem("B-1"))
item.appendRow(QStandardItem("B-2"))
tree_model.appendRow(item)
item = QStandardItem("C")
tree_model.appendRow(item)
print([_.data() for _ in model_iter(tree_model)])
>>> [u'A', u'A-1', u'A-2', u'B', u'B-1', u'B-2', u'C']
Es wird nicht nur der Baumtyp, sondern auch das Tabellentypmodell unterstützt.
table_model = QStandardItemModel(3, 3)
for r in range(3):
for c in range(3):
table_model.setItem(r, c, QStandardItem("%d-%d" % (r, c)))
print([_.data() for _ in model_iter(table_model)])
>>> [u'0-0', u'0-1', u'0-2', u'1-0', u'1-1', u'1-2', u'2-0', u'2-1', u'2-2']
Ich habe auch einen Reverse-Iterator erstellt.
def model_iter_r(model, parent_index=QModelIndex(), col_iter=True):
"""Modelliterator (umgekehrte Reihenfolge)
:rtype: generator(QModelIndex)
:type col_iter: bool
:type parent_index: QModelIndex
:type model: QAbstractItemModel
"""
index = model.index(model.rowCount(parent_index) - 1, 0, parent_index)
while True:
if model.rowCount(index) > 0:
for _ in model_iter_r(model, index, col_iter):
yield _
if col_iter:
for col in range(model.columnCount(parent_index) - 1, -1, -1):
yield index.sibling(index.row(), col)
else:
yield index
index = index.sibling(index.row() - 1, index.column())
if not index.isValid():
break
Die Nutzung ist genau die gleiche wie in der Reihenfolge.
print([_.data() for _ in model_iter_r(tree_model)])
>>> [u'C', u'B-2', u'B-1', u'B', u'A-2', u'A-1', u'A']
print([_.data() for _ in model_iter_r(table_model)])
>>> [u'2-2', u'2-1', u'2-0', u'1-2', u'1-1', u'1-0', u'0-2', u'0-1', u'0-0']
Die Baumstruktur wird ebenfalls in umgekehrter Reihenfolge verfolgt.
Der sequentielle Zugriff auf Modelle ist eine häufig verwendete Funktion, die Implementierung ist jedoch schwierig, da rekursive Funktionen verwendet werden. Es ist bequem, diese Funktion zu kopieren.
Das nächste Mal werden wir diese Funktion verwenden, um ein Suchobjekt zu erstellen.
Recommended Posts