通过返回迭代器来隐藏STL容器实现

时间:2012-04-06 18:35:36

标签: c++ stl iterator

我正在尝试做的是返回一个ForwardIterator(甚至是一对开始和结束迭代器),以便可以保持uderlying实现对客户端类隐藏。 我找不到任何这样的例子。

如果底层实现是vector,则迭代器是vector :: iterator ..即使你对输出进行模板化,这似乎也不起作用。

5 个答案:

答案 0 :(得分:2)

您不能同时按原样返回对象,并希望调用者不知道其类型。 “隐藏”任何对象的真实类型的典型方法是将其隐藏在界面后面。

例如,您可能希望编写如下内容:

template<typename T>
class Cursor
{
public:
    typedef T value_type;
    virtual ~Cursor () {}
    virtual bool has_result () = 0;
    virtual value_type get_result () = 0;
};

// implements cursor interface for any sequence
// described as a pair of forward iterators.
template<typename I>
class ForwardSequenceCursor :
    public Cursor<std::iterator_traits<I>::value_type>
{
    I myCurrent;
    const I myEnd;
public:
     ForwardSequenceCursor(I begin, I end)
         : myCurrent(current), myEnd(end)
     {}
     virtual bool has_result () {
         return myCurrent != myEnd;
     }
     virtual value_type get_result () {
         return *myCurrent++;
     }
};

然后,您可以返回任何正向序列:

class Foo
{
    std::vector<int> myValues;
public:
    std::unique_ptr< Cursor<int> > values () {
        return std::unique_ptr< Cursor<int> >(
            new ForwardSequenceCursor<vector<int>::const_iterator>(
                myValues.begin(), myValues.end()
            )
        );
    }
};

并像这样使用它:

std::unique_ptr< Cursor<int> > cursor = foo.values();
while (cursor->has_result()) {
    std::cout << cursor->get_result() << std::endl;
}

答案 1 :(得分:1)

答案 2 :(得分:1)

你无法直接做你想做的事情,因为正如其他人所说,如果你的客户要获得一个返回值,它需要知道返回值是什么。

一种方法是做这样的事情:

template<typename Collection> class MyClass
{
    typedef Collection::iterator ReturnIt;
    typedef std::pair<ReturnIt, ReturnIt> IteratorPair;
    ReturnIt foo();
    IteratorPair bar();
};

现在,这并没有让我们看到容器类型的客户端,但接口没有绑定到容器类型。

答案 3 :(得分:0)

ForwardIterator是一个概念,而不是一个类型。您需要声明函数以返回类型。

答案 4 :(得分:0)

没有类型为“ForwardIterator”的基类,正常的STL方式是在类中使用typedef到实际的迭代器类型,以便客户端代码可以像这样使用它:

  

MyClass :: iterator it = myclass.begin();

隐藏效果不是很好,但仍然允许您稍后更改实现,而无需更改客户端代码。