如何通常实现SQL选择

时间:2012-01-29 18:06:44

标签: c++ select

我有两个班级

class PopulationMember
{
public:
    void operationOnThisMember1();
    void operationOnThisMember2();
    ...

private:

    Population* populaltion_;
}

class Population
{
public:
    void operationOnAllMembers1();
    void operationOnAllMembers2();
    ...
    void operationOnAllMembers100();

    void sortAllMembersCriterium1();
    void sortAllMembersCriterium2();
    ...
    void sortAllMembersCriterium100();

private:
    QVector<PopulationMember*> members_;
}

我想在我的框架中实现类似SELECT的功能。这只能对那些共享特定属性组合的成员执行操作。

到目前为止,我已经考虑过两种方法:

  1. 实现一个方法,该方法将返回由满足特定条件的成员组成的新Population对象。

    Popuation Popuation::select(bool (predicate*) (PopulationMember*));
    
  2. 添加

    bool selected_; 
    

    标记每个人口成员。

  3. 如果我这样做1.无法实现所选数据的排序和删除。如果我这样做2.有检查选择性的开销,我将不得不重新实现排序和其他算法,只对选定的成员进行操作。

    还有第三种更好的方式吗?

3 个答案:

答案 0 :(得分:2)

我将采用的方法是将迭代器接口暴露给整个集合。为了实现某种选择,我将使用迭代器适配器,例如:一个采用一元谓词,提供范围的新视图。这样,既不会对存储的对象产生影响,也不会对创建单独的集合产生任何开销。如果你看看Boost的迭代器适配器,你可能已经得到了所需的东西。

答案 1 :(得分:1)

我从未看过,但我希望它是方法1.请参阅MySQL source code以确认我的期望。 : - )

答案 2 :(得分:1)

这是一个基于我曾经做过的类似事情的提议,这是你第一种方法的扩展形式。 优点是使用STL的概念,并且可以自由地实现许多仿函数或几个可参数化的仿函数。

class All
{
public:
    bool operator()(const PopulationMember* entity) const
    {
        return true;
    }
};

class AscByID
{
public:
    bool operator()(const PopulationMember* a, const PopulationMember* b) const
    {
        return a->getId() < b.getId();
    }
};

template<typename Entity, class Predicate, class SortComparator>
class Query
{
public:
    typedef std::set<Entity, SortComparator> ResultSet;

    Query(const Predicate& predicate = Predicate(), const SortComparator& cmp = SortComparator()) :
            predicate(predicate), resultSet(cmp)
    {
    }

    bool operator()(const Entity& entity)
    {
        if (predicate(entity))
        {
            resultSet.insert(entity);
            return true;
        }
        return false;
    }

    const ResultSet& getResult(void) const
    {
        return resultSet;
    }

    void clearResult(void)
    {
        resultSet.clear();
    }
private:
    Predicate predicate;
    ResultSet resultSet;
};

int main()
{
    Query<const PopulationMember*, All, AscByID> query;

    Popuation::execute(query);
    //do something with the result
    query.getResult();
    //clear the result
    query.clearResult();
    //query again
    Popuation::execute(query);
    //do something useful again
    return 0;
}