【问题标题】:How to optimize PyQt QSortFilterProxyModel filter reimplementation?如何优化 PyQt QSortFilterProxyModel 过滤器重新实现?
【发布时间】:2010-08-13 05:18:31
【问题描述】:

我有一个重新实现的 QSortFilterProxyModel acceptRows 来实现自定义行为,我希望它不会过滤掉具有有效子项的项目。

class KSortFilterProxyModel(QSortFilterProxyModel):
    #FIXME: Funciona pero es endemoniadamente lento
    def __init__(self, parent=None):
        super(KSortFilterProxyModel, self).__init__(parent)
        self.__showAllChildren = False

    def showAllChildren(self):
        return self.__showAllChildren;

    def setShowAllChildren(self, showAllChildren):
        if showAllChildren == self.__showAllChildren:
            return
        self.__showAllChildren = showAllChildren
        self.invalidateFilter()

    def filterAcceptsRow (self, source_row, source_parent ):
        if self.filterRegExp() == "" :
            return True #Shortcut for common case

        if  super(KSortFilterProxyModel, self).filterAcceptsRow( source_row, source_parent) :
            return True

        #one of our children might be accepted, so accept this row if one of our children are accepted.
        source_index = self.sourceModel().index(source_row, 0, source_parent)
        for i in range( self.sourceModel().rowCount(source_index)):
            if self.filterAcceptsRow(i, source_index):
                return True

        return False

但是这种方法似乎效率不高,因为有 300 个项目,更新视图需要将近 3 秒,我想知道是否有更好的方法。

PD:这个类基本上是我在KDE websvn 中找到的 KSysGuard 的翻译

【问题讨论】:

    标签: python qt4 pyqt pyqt4


    【解决方案1】:

    我看不出你所做的有什么明显的错误。请记住,模型中的每个项目都会调用filterAcceptsRow,这当然会很慢,因为从C++调用Python函数的开销只有几毫秒。如果您有一个包含几百个项目的模型,这会很快加起来。再加上从 Python 调用的 C++ 函数的数量,您可以轻松地以您注意到的 3 秒结束。

    另外,QTableViewQSortFilterProxyModel 做了很多聪明的事情来保持它们发出的信号和所需的更新量最少。遗憾的是,如果在过滤器重置后删除或添加的行非常分散在您的模型中,这会导致非常糟糕的性能。

    在我们的项目中,我们已决定在 C++ 中实现大多数这些基于项目的模型,至少对于那些为模型中包含大量行或列的每个项目调用的方法而言。但是,这可能不是您正在寻找的答案,特别是如果您的更新延迟是由例如连接到同一模型的其他信号处理程序。发出信号通常与调用方法相同。

    简而言之,您最好使用探查器来查看您的应用程序在哪里花费了大部分时间,如果在模型中每个项目被调用一次(甚至不止一次)的这些方法中,则使用 C++ .

    【讨论】:

    • 非常感谢,我宁愿不使用 C++,但我认为这是解决这个问题的方法。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-01-17
    • 2014-12-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多