5 #ifndef VCCC_RANGES_REND_HPP_
6 #define VCCC_RANGES_REND_HPP_
29 using vccc::detail::tag_1;
30 using vccc::detail::tag_2;
31 using vccc::detail::tag_3;
33 struct rend_niebloid {
37 struct rend_member_check : std::false_type {};
39 struct rend_member_check<T,
41 : sentinel_for<decltype(vccc_decay_copy( std::declval<T>().rend() )),
42 decltype( ranges::rbegin(std::declval<T>()) )> {};
44 template<
typename T,
bool = conjunction<
45 is_invocable<rbegin_niebloid, T&&>,
46 is_class_or_enum<remove_cvref_t<T>>>
::value,
typename =
void>
47 struct rend_global_check : std::false_type {};
49 struct rend_global_check<T,
51 : sentinel_for<decltype(vccc_decay_copy( rend(std::declval<T>()) )),
52 decltype( ranges::rbegin(std::declval<T>()) )> {};
55 struct common_bidi_check : std::false_type {};
57 struct common_bidi_check<T, true> : bidirectional_iterator<decltype( ranges::begin(std::declval<T>()) )> {};
60 using rend_tag = conditional_tag<rend_member_check<T>, rend_global_check<T>, common_bidi_check<T>>;
63 constexpr
auto run(T&& t, tag_1)
const {
68 constexpr
auto run(T&& t, tag_2)
const {
73 constexpr
auto run(T&& t, tag_3)
const {
78 template<
typename T, std::enable_if_t<conjunction<
79 vccc::detail::not_incomplete_array<T>,
81 std::is_lvalue_reference<std::remove_cv_t<T>>,
82 enable_borrowed_range<std::remove_cv_t<T>>
86 constexpr
auto operator()(T&& t)
const {
87 return run(std::forward<T>(t), rend_tag<T>{});
103 using namespace niebloid;
#define vccc_decay_copy(x)
Definition: decay_copy.hpp:12
constexpr VCCC_INLINE_OR_STATIC detail::rend_niebloid rend
Definition: rend.hpp:98
constexpr VCCC_INLINE_OR_STATIC detail::begin_niebloid begin
returns an iterator to the beginning of a range
Definition: begin.hpp:116
std::integral_constant< bool, v > bool_constant
Definition: bool_constant.hpp:19
#define VCCC_INLINE_OR_STATIC
Definition: inline_or_static.hpp:9
Definition: matrix.hpp:495
Definition: directory.h:12
constexpr VCCC_INLINE_OR_STATIC detail::element_niebloid< 1 > value
Definition: key_value.hpp:35