【问题标题】:Is QSortFilterProxyModel::filterAcceptRows customizable to accept functors?QSortFilterProxyModel::filterAcceptRows 是否可定制以接受函子?
【发布时间】:2015-02-16 16:09:53
【问题描述】:

我目前正在开发一个使用自定义模型作为 Qt 模型/视图结构扩展的应用程序。一个名为 MyModel 的模型存储了一个具有几千个元素的对象(比如 std::vector ),MyModel 中的数据使用标准的 QTableView 进行查看。但是,该应用程序支持对表格中查看的数据进行一些简单的基本过滤,包括按相关性、上传日期等进行过滤。

QSortFilterProxyModel 允许基于正则表达式对模型数据进行(排序和)过滤,但不幸的是,在 bool filterAcceptsRow( int const &, QModelIndex const & ) 中定义的过滤技术不允许传递自定义函子,这样functor 用作过滤函数,而不是在 filterAcceptsRow 中进行过滤。

这就是我要说的,假设一个人想在已经生成的乘法表( 12 x 12 )中找出所有偶数,目前我认为可以通过 QSortFilterProxyModel::filterAcceptsRow( ... ) 来实现

QSortFilterProxyModel::filterAcceptsRow( int source_row, ... )
{
    return sourceModel()->data( source_row ).toInt() % 2 == 0;
}

我想要的不仅仅是按偶数过滤,有没有一种方法可以通过将不同的函子传递给 filterAcceptsRow(...) 来进行各种过滤?像 std::sort( , , lambda_expression ) 或 std::for_each( , , lambda ) 等,因此按相关性、日期、时间过滤将调用相同的函数,但具有不同的函子。

编辑:我很抱歉格式很糟糕,我的手机可以做的很少

【问题讨论】:

  • 这是一个基于策略的类的精简实现。也许这样的东西是你正在寻找的? ideone.com/hsNTXn
  • 这可行,但我希望看到更多可能的方式来实现相同的目标,感谢 PaulMcKenzie

标签: c++ qt c++11


【解决方案1】:

根据docs - 不,不是。 filterAcceptsRow() 的目的是提供定制机制。

自定义过滤行为可以通过重新实现 filterAcceptsRow() 和 filterAcceptsColumn() 函数来实现。

因此,您可以通过一些支持filterAcceptsRow() 中的函子的修改来实现您的自定义 QSortFilterProxyModel。例如:

class FilterFunc
{
protected:
    const QSortFilterProxyModel * proxy_;
public:
    FilterFunc() : proxy_(0) {}
    FilterFunc(const QSortFilterProxyModel * p) : proxy_(p) {}
    bool operator()(int source_row, const QModelIndex & source_parent) {return true;}
};

class CustomSortFilterProxyModel : public QSortFilterProxyModel
{
    Q_OBJECT
    FilterFunc filter_;
protected:
    virtual bool filterAcceptsRow(int source_row, const QModelIndex & source_parent) const {
        return filter_(source_row, source_parent);
    }
public:
    void setFilter(FilterFunc f) {filter_ = f;}
};

用法:

struct CustomFilter : public FilterFunc
{
    bool operator()(int source_row, const QModelIndex & source_parent) {
        return proxy_->sourceModel()->data( source_row ).toInt() % 2 == 0;
    }
};

//...

CustomSortFilterProxyModel pm;
pm.setFilter(CustomFilter(&pm));
...
//operations that will call filterAcceptsRow()

要使用 C++11 lambda - 将 FilterFunc 替换为 std::function,将第三个参数添加到 filterAcceptsRow() - QSortFilterProxyModel 类型的对象,然后使用 std::bind

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-11-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-12-30
    • 1970-01-01
    相关资源
    最近更新 更多