std::ranges::rend
| ヘッダ <ranges> で定義 |
||
| ヘッダ <iterator> で定義 |
||
| inline namespace /* 未指定 */ { inline constexpr /* unspecified */ rend = /* unspecified */; |
(C++20以降) (カスタマイズポイントオブジェクト) |
|
| 呼び出しシグネチャ |
||
| template< class T > requires /* 以下を参照 */ |
(C++20以降) | |
逆順範囲の終端を示すセンチネルを返します。
T が配列型であり、std::remove_all_extents_t<std::remove_reference_t<T>> が不完全型の場合、ranges::rend の呼び出しは不正形式となり、診断は要求されません。
引数が左辺値であるか、または ranges::enable_borrowed_range<std::remove_cv_t<T>> が true の場合、ranges::rend の呼び出しは、
- decay-copy(t.rend())(until C++23)auto(t.rend())(since C++23) と式等価です。
- それ以外の場合、decay-copy(rend(t))(until C++23)auto(rend(t))(since C++23) は、
Tがクラス型または列挙型であり、その式が有効で、その型が std::sentinel_for<decltype(ranges::rbegin(std::declval<T>()))> をモデルとする場合に有効であり、この場合の `rend` の意味は、引数依存探索のみを実行した場合のそれと同様に確立されます。 - それ以外の場合、std::make_reverse_iterator(ranges::begin(t)) は、ranges::begin(t) と ranges::end(t) の両方が有効な式であり、同じ型を持ち、その型が std::bidirectional_iterator をモデルとする場合に有効です。
それ以外の場合、ranges::rend の呼び出しは不正形式となり、テンプレートインスタンス化の直接のコンテキストに ranges::rend(t) が現れると SFINAE の原因となることがあります。
目次 |
カスタマイゼーションポイントオブジェクト
ranges::rend という名前は、関数オブジェクトであり、リテラルな semiregular クラス型の定数である *customization point object* を示します。説明のために、その型の cv-unqualified バージョンは __rend_fn と表記されます。
__rend_fn のすべてのインスタンスは等価です。同じ引数に対して異なる __rend_fn 型のインスタンスを呼び出す効果は、インスタンスを示す式が左辺値か右辺値か、または const 修飾されているかどうかにかかわらず同等です(ただし、volatile 修飾されたインスタンスは呼び出し可能である必要はありません)。したがって、ranges::rend は自由にコピーでき、そのコピーは相互に交換可能に使用できます。
型のセット Args... が与えられた場合、std::declval<Args>()... が上記の ranges::rend の引数要件を満たす場合、__rend_fn は以下をモデルとします。
- std::invocable<__rend_fn, Args...>,
- std::invocable<const __rend_fn, Args...>,
- std::invocable<__rend_fn&, Args...>、および
- std::invocable<const __rend_fn&, Args...>.
それ以外の場合、__rend_fn の関数呼び出し演算子のいずれもオーバーロード解決に参加しません。
[編集] 注記
引数が右辺値(つまり T がオブジェクト型)であり、ranges::enable_borrowed_range<std::remove_cv_t<T>> が false であるか、または未知の境界を持つ配列型である場合、ranges::rend の呼び出しは不正形式となり、これも SFINAE の原因となります。
もし ranges::rend(std::forward<T>(t)) が有効であるなら、decltype(ranges::rend(std::forward<T>(t))) と decltype(ranges::begin(std::forward<T>(t))) はすべてのケースで std::sentinel_for をモデルとし、一方 T は std::ranges::range をモデルとします。
C++20 標準は、基となる rend 関数呼び出しが prvalue を返す場合、その戻り値はマテリアライズされた一時オブジェクトからムーブ構築されることを要求しています。すべての実装は代わりに prvalue を直接返します。この要件は、実装に合わせるために C++20 以降の提案 P0849R8 によって修正されています。
[編集] 例
#include <algorithm> #include <iostream> #include <ranges> #include <vector> int main() { std::vector<int> v = {3, 1, 4}; namespace ranges = std::ranges; if (ranges::find(ranges::rbegin(v), ranges::rend(v), 5) != ranges::rend(v)) std::cout << "found a 5 in vector v!\n"; int a[] = {5, 10, 15}; if (ranges::find(ranges::rbegin(a), ranges::rend(a), 5) != ranges::rend(a)) std::cout << "found a 5 in array a!\n"; }
出力
found a 5 in array a!
[編集] 不具合報告
以下の動作変更を伴う欠陥報告が、以前に公開されたC++標準に遡って適用されました。
| DR | 適用対象 | 公開された動作 | 正しい動作 |
|---|---|---|---|
| P2602R2 | C++20 | ADL によって見つかる特定の非メンバ rend を禁止する仕組みがあります。 |
その仕組みは削除されました。 |
[編集] 関連項目
| (C++20) |
読み取り専用rangeへの逆終端イテレータを返す (カスタマイゼーションポイントオブジェクト) |
| (C++20) |
rangeへの逆イテレータを返す (カスタマイゼーションポイントオブジェクト) |
| (C++14) |
コンテナまたは配列の逆順の終端イテレータを返す (function template) |