std::reverse_iterator
| ヘッダ <iterator> で定義 |
||
| template< class Iter > class reverse_iterator; |
||
std::reverse_iterator は、指定されたイテレータの方向を反転させるイテレータアダプタです。指定されたイテレータは、少なくとも LegacyBidirectionalIterator または bidirectional_iterator のモデル(C++20 以降)である必要があります。言い換えれば、双方向イテレータが与えられると、std::reverse_iterator は、基礎となる双方向イテレータによって定義されるシーケンスの末尾から先頭へ移動する新しいイテレータを生成します。
イテレータ i から構築された逆イテレータ r の場合、関係 &*r == &*(i - 1) は常に true です (r が 逆参照可能である限り)。したがって、範囲外イテレータから構築された逆イテレータは、シーケンスの最後の要素を逆参照します。
これは、標準ライブラリコンテナのメンバー関数 rbegin() と rend() によって返されるイテレータです。
目次 |
[編集] ネストされた型
|
(C++20まで) | ||||||||||||||||
|
(C++20以降) |
- ↑ 1.0 1.1 この定義は、C++17までは基底の std::iterator 特殊化によって提供されます。
[編集] データメンバー
| メンバ | 説明 |
Iter current |
基礎となるイテレータ (protected member object) |
[編集] メンバー関数
新しい reverse_iterator を構築する(public member function) | |
別の reverse_iterator を代入する(public member function) | |
| 基底イテレータにアクセスする (public member function) | |
| 指し示す要素にアクセスする (public member function) | |
| インデックスで要素にアクセスする (public member function) | |
reverse_iterator を進めるかデクリメントする(public member function) |
[編集] 非メンバー関数
| 基底イテレータを比較する (関数テンプレート) | |
| イテレータを進める (関数テンプレート) | |
| 2つのイテレータアダプタ間の距離を計算する (関数テンプレート) | |
| (C++20) |
調整された基礎となるイテレータの逆参照結果を、関連する右辺値参照型にキャストする (関数) |
| (C++20) |
2つの調整された基礎となるイテレータが指すオブジェクトをスワップする (関数テンプレート) |
| (C++14) |
引数から型が推論される std::reverse_iterator を作成する (関数テンプレート) |
[編集] ヘルパーテンプレート
| template< class Iterator1, class Iterator2 > requires (!std::sized_sentinel_for<Iterator1, Iterator2>) |
(C++20以降) | |
std::disable_sized_sentinel_for のこの部分特殊化は、基礎となるイテレータがコンセプトを満たさない場合、reverse_iterator の特殊化が sized_sentinel_for を満たすことを妨げます。
[編集] 可能な実装
以下は、内部イテレータの格納方法に焦点を当てた部分的な実装であり、コンテンツが operator* を介してフェッチされる場合にのみ std::prev を呼び出します。
template<class It> class reverse_iterator { protected: It current = It(); public: reverse_iterator() = default; constexpr explicit reverse_iterator(It itr) : current(itr) {} template<class U> requires (!std::is_same_v<U, It> && std::convertible_to<const U&, It>) constexpr explicit reverse_iterator(const U& other) : current(other.base()) {} constexpr decltype(auto) operator*() const { return *std::prev(current); // <== returns the content of prev } constexpr reverse_iterator& operator++() { --current; return *this; } constexpr reverse_iterator operator++(int) { auto tmp = *this; ++(*this); return tmp; } constexpr reverse_iterator& operator--() { ++current; return *this; } constexpr reverse_iterator operator--(int) { auto tmp = *this; --(*this); return tmp; } constexpr It base() const { return current; } // Other member functions, friend functions, and member typedefs are not shown here. }; |
[編集] 備考
std::reverse_iterator は、逆参照が *this のメンバへの参照を返すイテレータ (いわゆる「スタッシングイテレータ」) では動作しません。スタッシングイテレータの例は、MSVC STL の std::filesystem::path::iterator です。
[編集] 例
#include <cstddef> #include <iostream> #include <iterator> template<typename T, std::size_t SIZE> class Stack { T arr[SIZE]; std::size_t pos = 0; public: T pop() { return arr[--pos]; } Stack& push(const T& t) { arr[pos++] = t; return *this; } // we wish that looping on Stack would be in LIFO order // thus we use std::reverse_iterator as an adaptor to existing iterators // (which are in this case the simple pointers: [arr, arr + pos) auto begin() { return std::reverse_iterator(arr + pos); } auto end() { return std::reverse_iterator(arr); } }; int main() { Stack<int, 8> s; s.push(5).push(15).push(25).push(35); for (int val : s) std::cout << val << ' '; std::cout << '\n'; }
出力
35 25 15 5
[編集] 関連項目
| (C++14) |
引数から型が推論される std::reverse_iterator を作成する (関数テンプレート) |
| (C++17で非推奨) |
単純なイテレータに必要な型の定義を容易にするための基底クラス (クラステンプレート) |