2009-07-10 86 views
14

我有一個類是否可以從任意迭代器(C++)獲取值類型?

template <typename Iterator, typename Value> 
class Foo { 
public: 
    Foo(const Iterator& it) { ... } 
    ... 
private: 
    map<Value, int> m_; 
    } 
}; 

有沒有辦法在模板中擺脫價值?迭代器可能是也可能不是STL迭代器,但它確保*它的類型是Value。

我知道關於STL迭代器的iterator_traits<T>::value_type,但想知道是否有任何方法可以爲任意迭代器類型自動獲取Value類型?

一招我在想 - 比方說,我們有一個輔助類

template <typename Iterator, typename Value> 
class Bar { 
public: 
    Bar(const Iterator& dummy_iterator, const Value& dummmy_value) {} 
    ... 
}; 

然後如果我們實例酒吧,酒吧(它,*它),值的類型將裏面酒吧是已知的。但是我找不到將Bar與Foo結合的好方法。

回答

18

任何迭代器應該提供iterator_traits<Iterator>::value_type。如果不是,那麼它不是迭代器。 ISO C++ 2003 24.3.1 [lib.iterator.traits]「迭代特徵」:

爲了實現算法僅在術語迭代 ,它通常需要 確定該值和差 類型對應於一個特定的 迭代器類型。因此,它是 必需的:如果Iterator是一個迭代的 類型,類型

iterator_traits<Iterator>::difference_type 
iterator_traits<Iterator>::value_type 
iterator_traits<Iterator>::iterator_category 

被定義爲迭代器的 差類型,值和類型迭代 類別,分別。

除此之外,沒有通用的方法來獲取任意C++表達式的類型。 C++ 0x將通過提供decltype來糾正它。

+0

謝謝,所述參考ISO C++標準是有幫助的。 – 2009-07-10 18:10:50

1

對不起。根據您的建議,擺脫Value的正確方法是使用iterator_traits

如果你的非STL迭代器是一個裸指針,那麼你可以免費得到正確的iterator_traits typedefs。否則,非STL迭代器類必須定義正確的typedef。

查看iterator traits documentation瞭解更多信息。

1

至於獲取迭代器的值類型以前的答案是正確的。

但還有更多。你正在考慮的訣竅不適合上課。如果Bar就像一個功能:

template <typename Iterator, typename Value> 
void bar(const Iterator& dummy_iterator, const Value& dummmy_value) {} 

然後類型推演將努力爲bar(it, *it),你將有bar內的值類型。 (但請記住,要使用這個技巧,你仍然必須有一個可忽略的迭代器,它並不總是很好 - 那麼如何處理空序列呢?)

使用類Bar你必須手動提供模板參數IteratorValue,因爲是上課沒有類型推演和使用Bar(it, *it)會沒有編譯。

+0

謝謝!我想到了使用bar作爲函數的相同之處,但是也許我錯過了一些東西。 – 2009-07-10 18:12:42

相關問題