2010-10-31 79 views
0

我正在为我的科学软件实现一个具有STL类接口的自定义容器,用于3D网格控件。这是关于这个容器的迭代器类的第二个问题。感谢您帮助我the first常量和非常量迭代器的单一类。可能吗?

我的问题就像"How do you avoid code duplication when implementing const and non-const iterators?"。我只想问是否可以提供无模板解决方案? (!而如果没有提供第二常量迭代器类)

的迭代器类看起来是这样的:


class spGridIterator { 
public: 
    typedef forward_iterator_tag iterator_category; 
    typedef spGridNode value_type; 
    typedef int difference_type; 
    typedef spGridNode* pointer; 
    typedef spGridNode& reference; 

    spGridIterator(); 
    spGridIterator(spGrid* gr, int index); 
    spGridIterator(const spGridIterator& orig); 
    virtual ~spGridIterator(); 

    // STL-ные операторы итератора 
    bool operator == (const spGridIterator& hs) const { 
     return (m_grid == hs.m_grid) && (m_idx == hs.m_idx); 
    } 

    bool operator != (const spGridIterator& hs) const { 
     return (m_grid != hs.m_grid) || (m_idx != hs.m_idx); 
    } 

    // non-const operators 
    spGridIterator& operator++(); 
    spGridIterator& operator++(int); 

    reference operator*() const; 
    pointer operator->() const { return &(operator*()); } 

private: 
    spGrid* m_grid; 
    int m_idx; 
}; 

和实施...

spGridIterator::spGridIterator(spGrid* gr, int index) { 
    m_grid = gr; 
    m_idx = index; 
} 

spGridIterator& spGridIterator::operator++() 
{ 
    int last = m_grid->numpoints; 

    if (m_idx < last) { 
     m_idx++; 
    } 
    return *this; 
} 

spGridIterator& spGridIterator::operator++(int) { 
    return operator++(); 
} 

spGridIterator::reference spGridIterator::operator*() const { 
    return (m_grid->GetNode(m_idx)); 
} 

我查了doctor dobbs article有关自定义迭代器实现。他们建议实施一个迭代器类模板并为value_type添加一个额外的模板参数。

那么,第二个解决方案是提供一个常规的迭代器和一个常量迭代器类。

是否有第三,也许“有点哈克”,单类无模板解决方案?也许提供一个转换运算符或额外的const版本operator++()

感谢, 伊利亚

+0

您的'运算符++(int)'返回错误的值 - 它是后缀'++',所以它应该返回iterator * prior *的副本以增加,而不是迭代后对迭代器*的引用。规范实现是Iterator Iterator :: operator ++(int){Iterator old = * this; ++(*此);回老; }' – 2010-10-31 18:35:28

+0

我明白了!感谢您的宝贵意见! – ezpresso 2010-10-31 18:56:06

+0

我不是真的需要我不会实现postfix ++运算符。你真的想鼓励使用前缀++运算符而不是后缀++运算符的人。 – Patrick 2010-10-31 19:44:57

回答

1

如果你想要去的那种哈克,你可以滥用“的const_cast”创建一个常量迭代出一个非const之一。

+0

简单的伎俩,但它的作品。不要忘记在源代码中清楚地评论为什么滥用const_cast。否则,下一个阅读代码的开发人员会认为你犯了一个错误,并且会想纠正你的错误,这个骗局。 – Patrick 2010-10-31 19:43:24