std::ranges::rbegin
Определено в заголовке <ranges> | ||
|---|---|---|
Определено в заголовке <iterator> | ||
inline namespace /* unspecified */ {
inline constexpr /* unspecified */ rbegin = /* unspecified */;
}
| (с C++20) (объект точки кастомизации) | |
| Подпись вызова | ||
template< class T >
requires /* see below */
constexpr std::input_or_output_iterator auto rbegin( T&& t );
| (с C++20) |
Возвращает итератор к последнему элементу аргумента.
Если T - тип массива, и std::remove_all_extents_t<std::remove_reference_t<T>> неполный, то вызов ranges::rbegin некорректен, диагностика не требуется.
Если аргумент является ссылочным значением или ranges::enable_borrowed_range<std::remove_cv_t<T>> является true, то вызов ranges::rbegin эквивалентен выражению:
-
decay-copy(t.rbegin())(до C++23)auto(t.rbegin())(с C++23), если это выражение корректно и его тип удовлетворяетstd::input_or_output_iterator. - В противном случае,
decay-copy(rbegin(t))(до C++23)auto(rbegin(t))(с C++23), еслиTявляется классом или перечислением, это выражение корректно и его тип удовлетворяетstd::input_or_output_iterator, где смыслrbeginустанавливается как если бы выполнялся поиск зависимых от аргументов только. - В противном случае,
std::make_reverse_iterator(ranges::end(t))еслиranges::begin(t)иranges::end(t)— корректные выражения, имеющие одинаковый тип и удовлетворяющиеstd::bidirectional_iterator.
Во всех остальных случаях вызов ranges::rbegin некорректен, что может привести к ошибке подстановки, когда ranges::rbegin(t) появляется в непосредственном контексте шаблона.
Объекты точки кастомизации
Название ranges::rbegin обозначает объект точки кастомизации, который является константным функциональным объектом литерального semiregular типа класса. Для удобства изложения, неквалифицированная версия его типа обозначается как __rbegin_fn.
Все экземпляры __rbegin_fn равны. Эффекты вызова разных экземпляров типа __rbegin_fn с одинаковыми аргументами эквивалентны, независимо от того, является ли выражение, обозначающее экземпляр, lvalue или rvalue, и является ли оно квалифицированным как const или нет (хотя экземпляр с квалификацией volatile не обязан быть вызываемым). Таким образом, ranges::rbegin можно свободно копировать, а его копии можно использовать взаимозаменяемо.
Учитывая набор типов Args..., если std::declval<Args>()... удовлетворяют требованиям аргументов для ranges::rbegin выше, __rbegin_fn удовлетворяет
-
std::invocable<__rbegin_fn, Args...>, -
std::invocable<const __rbegin_fn, Args...>, -
std::invocable<__rbegin_fn&, Args...>, и -
std::invocable<const __rbegin_fn&, Args...>.
В противном случае, ни один оператор вызова функции __rbegin_fn не участвует в разрешении перегрузки.
Примечания
Если аргумент является rvalue (т.е. T является типом объекта) и ranges::enable_borrowed_range<std::remove_cv_t<T>> является false, вызов ranges::rbegin некорректен, что также приводит к ошибке подстановки.
Тип возврата во всех случаях удовлетворяет std::input_or_output_iterator.
Стандарт C++20 требует, чтобы если основной вызов функции rbegin возвращает prvalue, значение возврата создавалось по движку из объекта временного объекта. Все реализации напрямую возвращают prvalue вместо этого. Требование исправлено предложением P0849R8 после C++20, чтобы соответствовать реализациям.
Пример
#include <iostream>
#include <ranges>
#include <span>
#include <vector>
int main()
{
std::vector<int> v = {3, 1, 4};
auto vi = std::ranges::rbegin(v);
std::cout << *vi << '\n';
*vi = 42; // OK
int a[] = {-5, 10, 15};
auto ai = std::ranges::rbegin(a);
std::cout << *ai << '\n';
*ai = 42; // OK
// auto x_x = std::ranges::rbegin(std::vector{6, 6, 6});
// ill-formed: the argument is an rvalue (see Notes ↑)
auto si = std::ranges::rbegin(std::span{a}); // OK
static_assert(std::ranges::enable_borrowed_range<
std::remove_cv_t<decltype(std::span{a})>>);
*si = 42; // OK
}Вывод:
4 15
Отчеты об ошибках
Следующие отчеты об ошибках, изменяющих поведение, были применены ретроактивно к ранее опубликованным стандартам C++.
| DR | Применено к | Поведение, как опубликовано | Правильное поведение |
|---|---|---|---|
| P2602R2 | C++20 | существует механизм для запрета некоторых нечленных rbegin, найденных с помощью ADL | такой механизм удален |
См. также
|
(C++20) | возвращает обратный итератор к только для чтения диапазону (объект точки кастомизации) |
|
(C++14) | возвращает обратный итератор к началу контейнера или массива (функция-шаблон) |
© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/w/cpp/ranges/rbegin