![](/img/trans.png)
[英]How is std::advance implemented to change behavior on iterator type?
[英]How std::advance iterator type is deduced?
請看一下std::advance
函數。 根據cppreference,復雜性是:
線性。 但是,如果InputIt另外滿足RandomAccessIterator的要求,則復雜性是不變的。
因此,如果我傳遞一個迭代器和一個整數,程序如何推導它是什么迭代器以及它是如何實現的? 那么這個功能有2個重載或者是什么?
程序如何推導出迭代器及其實現方式?
它使用std::iterator_traits<T>::iterator_category
來確定迭代器類別,然后執行標記調度 。
std::iterator_traits
專門用於原始指針。 原始指針是隨機訪問迭代器。
例如:
template<class I>
void doadvance(I& i, size_t n, std::random_access_iterator_tag) {
i += n;
}
template<class I, class Tag>
void doadvance(I& i, size_t n, Tag) {
while(n--)
++i;
}
template<class I>
void advance(I& i, size_t n) {
using Tag = typename std::iterator_traits<I>::iterator_category;
doadvance(i, n, Tag{});
}
在C ++ 17而不是標簽調度中,它可以使用if constexpr
,但這會使標准庫不向后兼容。 這就是為什么它必須繼續使用標簽調度 。
IMO, std::next
有一個比std::advance
更好的接口,因為它返回迭代器,因此調用不必占用自己的代碼行。
程序如何推導它是什么迭代器
std::iterator_traits
被使用,即std::iterator_traits<It>::iterator_category
將被檢查,並且如果它是std::random_access_iterator_tag
,意味着它是一個RandomAccessIterator的。
BTW: std::iterator_traits
專門用於原始指針; 他們總是RandomAccessIterator。
那么這個功能有2個重載或者是什么?
std::advance
不再有重載,實現通常會實現幾個輔助函數重載,這些重載根據std::advance
的iterator_category調用。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.