Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-12-15 10:26:44

0001 /// \file
0002 // Range v3 library
0003 //
0004 //  Copyright Eric Niebler 2013-present
0005 //
0006 //  Use, modification and distribution is subject to the
0007 //  Boost Software License, Version 1.0. (See accompanying
0008 //  file LICENSE_1_0.txt or copy at
0009 //  http://www.boost.org/LICENSE_1_0.txt)
0010 //
0011 // Project home: https://github.com/ericniebler/range-v3
0012 //
0013 
0014 #ifndef RANGES_V3_UTILITY_TUPLE_ALGORITHM_HPP
0015 #define RANGES_V3_UTILITY_TUPLE_ALGORITHM_HPP
0016 
0017 #include <initializer_list>
0018 #include <tuple>
0019 #include <type_traits>
0020 #include <utility>
0021 
0022 #include <meta/meta.hpp>
0023 
0024 #include <range/v3/range_fwd.hpp>
0025 
0026 #include <range/v3/detail/adl_get.hpp>
0027 #include <range/v3/functional/invoke.hpp>
0028 #include <range/v3/utility/static_const.hpp>
0029 
0030 #include <range/v3/detail/prologue.hpp>
0031 
0032 namespace ranges
0033 {
0034     /// \addtogroup group-utility
0035     /// @{
0036     template<typename Tup>
0037     using tuple_indices_t = meta::make_index_sequence<
0038         std::tuple_size<typename std::remove_reference<Tup>::type>::value>;
0039 
0040     struct tuple_apply_fn
0041     {
0042         // clang-format off
0043     private:
0044         template<typename Fun, typename Tup, std::size_t... Is>
0045         static constexpr auto //
0046         CPP_auto_fun(impl)(Fun &&fun, Tup &&tup, meta::index_sequence<Is...>)
0047         (
0048             return invoke(static_cast<Fun &&>(fun),
0049                           detail::adl_get<Is>(static_cast<Tup &&>(tup))...)
0050         )
0051     public:
0052         template<typename Fun, typename Tup>
0053         constexpr auto CPP_auto_fun(operator())(Fun &&fun, Tup &&tup)(const)
0054         (
0055             return tuple_apply_fn::impl(static_cast<Fun &&>(fun),
0056                                         static_cast<Tup &&>(tup),
0057                                         tuple_indices_t<Tup>{})
0058         )
0059         // clang-format on
0060     };
0061 
0062     /// \ingroup group-utility
0063     /// \sa `tuple_apply_fn`
0064     RANGES_INLINE_VARIABLE(tuple_apply_fn, tuple_apply)
0065 
0066     struct tuple_transform_fn
0067     {
0068         // clang-format off
0069     private:
0070         template<typename Tup, typename Fun, std::size_t... Is>
0071         static constexpr auto //
0072         CPP_auto_fun(impl1)(Tup &&tup, Fun &fun, meta::index_sequence<Is...>)
0073         (
0074             return std::tuple<
0075                 decltype(fun(detail::adl_get<Is>(static_cast<Tup &&>(tup))))...>{
0076                 fun(detail::adl_get<Is>(static_cast<Tup &&>(
0077                     tup)))...}
0078         )
0079         template<typename Tup0, typename Tup1, typename Fun, std::size_t... Is>
0080         static constexpr auto CPP_auto_fun(impl2)(Tup0 &&tup0, Tup1 &&tup1, Fun &fun,
0081                                         meta::index_sequence<Is...>)
0082         (
0083             return std::tuple<
0084                 decltype(fun(detail::adl_get<Is>(static_cast<Tup0 &&>(tup0)),
0085                              detail::adl_get<Is>(static_cast<Tup1 &&>(tup1))))...>{
0086                 fun(detail::adl_get<Is>(static_cast<Tup0 &&>(tup0)),
0087                     detail::adl_get<Is>(static_cast<Tup1 &&>(tup1)))...}
0088         )
0089     public:
0090         template<typename Tup, typename Fun>
0091         constexpr auto CPP_auto_fun(operator())(Tup &&tup, Fun fun)(const)
0092         (
0093             return tuple_transform_fn::impl1(
0094                 static_cast<Tup &&>(tup), fun,
0095                 tuple_indices_t<Tup>{})
0096         )
0097         template<typename Tup0, typename Tup1, typename Fun>
0098         constexpr auto CPP_auto_fun(operator())(Tup0 &&tup0, Tup1 &&tup1, Fun fun)(const)
0099         (
0100             return tuple_transform_fn::impl2(static_cast<Tup0 &&>(tup0),
0101                                              static_cast<Tup1 &&>(tup1), fun,
0102                                              tuple_indices_t<Tup0>{})
0103         )
0104         // clang-format on
0105     };
0106 
0107     /// \ingroup group-utility
0108     /// \sa `tuple_transform_fn`
0109     RANGES_INLINE_VARIABLE(tuple_transform_fn, tuple_transform)
0110 
0111     struct tuple_foldl_fn
0112     {
0113     private:
0114         template<typename Tup, typename Val, typename Fun>
0115         static constexpr Val impl(Tup &&, Val val, Fun &)
0116         {
0117             return val;
0118         }
0119         // clang-format off
0120         template<std::size_t I0, std::size_t... Is, typename Tup, typename Val,
0121                  typename Fun, typename Impl = tuple_foldl_fn>
0122         static constexpr auto CPP_auto_fun(impl)(Tup &&tup, Val val, Fun &fun)
0123         (
0124             return Impl::template impl<Is...>(
0125                 static_cast<Tup &&>(tup),
0126                 fun(std::move(val), detail::adl_get<I0>(static_cast<Tup &&>(tup))),
0127                 fun)
0128         )
0129         template<typename Tup, typename Val, typename Fun, std::size_t... Is>
0130         static constexpr auto CPP_auto_fun(impl2)(Tup &&tup, Val val, Fun &fun,
0131                                         meta::index_sequence<Is...>)
0132         (
0133             return tuple_foldl_fn::impl<Is...>(static_cast<Tup &&>(tup),
0134                                                std::move(val),
0135                                                fun)
0136         )
0137     public:
0138         template<typename Tup, typename Val, typename Fun>
0139         constexpr auto CPP_auto_fun(operator())(Tup &&tup, Val val, Fun fun)(const)
0140         (
0141             return tuple_foldl_fn::impl2(static_cast<Tup &&>(tup),
0142                                          std::move(val),
0143                                          fun,
0144                                          tuple_indices_t<Tup>{})
0145         )
0146         // clang-format on
0147     };
0148 
0149     /// \ingroup group-utility
0150     /// \sa `tuple_foldl_fn`
0151     RANGES_INLINE_VARIABLE(tuple_foldl_fn, tuple_foldl)
0152 
0153     struct tuple_for_each_fn
0154     {
0155     private:
0156         template<typename Tup, typename Fun, std::size_t... Is>
0157         static constexpr void impl(Tup && tup, Fun & fun, meta::index_sequence<Is...>)
0158         {
0159             (void)std::initializer_list<int>{
0160                 ((void)fun(detail::adl_get<Is>(static_cast<Tup &&>(tup))), 42)...};
0161         }
0162 
0163     public:
0164         template<typename Tup, typename Fun>
0165         constexpr Fun operator()(Tup && tup, Fun fun) const
0166         {
0167             return tuple_for_each_fn::impl(
0168                        static_cast<Tup &&>(tup), fun, tuple_indices_t<Tup>{}),
0169                    fun;
0170         }
0171     };
0172 
0173     /// \ingroup group-utility
0174     /// \sa `tuple_for_each_fn`
0175     RANGES_INLINE_VARIABLE(tuple_for_each_fn, tuple_for_each)
0176 
0177     struct make_tuple_fn
0178     {
0179         // clang-format off
0180         template<typename... Ts>
0181         constexpr auto CPP_auto_fun(operator())(Ts &&... ts)(const)
0182         (
0183             return std::make_tuple(static_cast<Ts &&>(ts)...)
0184         )
0185         // clang-format on
0186     };
0187 
0188     /// \ingroup group-utility
0189     /// \sa `make_tuple_fn`
0190     RANGES_INLINE_VARIABLE(make_tuple_fn, make_tuple)
0191     /// @}
0192 } // namespace ranges
0193 
0194 #include <range/v3/detail/epilogue.hpp>
0195 
0196 #endif