Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-12-17 10:23:59

0001 /// \file
0002 // Range v3 library
0003 //
0004 //  Copyright Eric Niebler 2014-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 #ifndef RANGES_V3_ALGORITHM_TRANSFORM_HPP
0014 #define RANGES_V3_ALGORITHM_TRANSFORM_HPP
0015 
0016 #include <utility>
0017 
0018 #include <meta/meta.hpp>
0019 
0020 #include <range/v3/range_fwd.hpp>
0021 
0022 #include <range/v3/algorithm/result_types.hpp>
0023 #include <range/v3/functional/identity.hpp>
0024 #include <range/v3/functional/invoke.hpp>
0025 #include <range/v3/iterator/concepts.hpp>
0026 #include <range/v3/iterator/traits.hpp>
0027 #include <range/v3/iterator/unreachable_sentinel.hpp>
0028 #include <range/v3/range/access.hpp>
0029 #include <range/v3/range/concepts.hpp>
0030 #include <range/v3/range/dangling.hpp>
0031 #include <range/v3/range/traits.hpp>
0032 #include <range/v3/utility/static_const.hpp>
0033 
0034 #include <range/v3/detail/prologue.hpp>
0035 
0036 namespace ranges
0037 {
0038     /// \addtogroup group-algorithms
0039     /// @{
0040     template<typename I, typename O>
0041     using unary_transform_result = detail::in_out_result<I, O>;
0042 
0043     template<typename I1, typename I2, typename O>
0044     using binary_transform_result = detail::in1_in2_out_result<I1, I2, O>;
0045 
0046     RANGES_FUNC_BEGIN(transform)
0047 
0048         // Single-range variant
0049         /// \brief function template \c transform
0050         template(typename I, typename S, typename O, typename F, typename P = identity)(
0051             requires input_iterator<I> AND sentinel_for<S, I> AND
0052             weakly_incrementable<O> AND copy_constructible<F> AND
0053             indirectly_writable<O, indirect_result_t<F &, projected<I, P>>>)
0054         constexpr unary_transform_result<I, O> //
0055         RANGES_FUNC(transform)(I first, S last, O out, F fun, P proj = P{}) //
0056         {
0057             for(; first != last; ++first, ++out)
0058                 *out = invoke(fun, invoke(proj, *first));
0059             return {first, out};
0060         }
0061 
0062         /// \overload
0063         template(typename Rng, typename O, typename F, typename P = identity)(
0064             requires input_range<Rng> AND weakly_incrementable<O> AND
0065             copy_constructible<F> AND
0066             indirectly_writable<O, indirect_result_t<F &, projected<iterator_t<Rng>, P>>>)
0067         constexpr unary_transform_result<borrowed_iterator_t<Rng>, O> //
0068         RANGES_FUNC(transform)(Rng && rng, O out, F fun, P proj = P{}) //
0069         {
0070             return (*this)(
0071                 begin(rng), end(rng), std::move(out), std::move(fun), std::move(proj));
0072         }
0073 
0074         // Double-range variant, 4-iterator version
0075         /// \overload
0076         template(typename I0,
0077                  typename S0,
0078                  typename I1,
0079                  typename S1,
0080                  typename O,
0081                  typename F,
0082                  typename P0 = identity,
0083                  typename P1 = identity)(
0084             requires input_iterator<I0> AND sentinel_for<S0, I0> AND
0085                 input_iterator<I1> AND sentinel_for<S1, I1> AND
0086                 weakly_incrementable<O> AND copy_constructible<F> AND
0087                 indirectly_writable<
0088                     O,
0089                     indirect_result_t<F &, projected<I0, P0>, projected<I1, P1>>>)
0090         constexpr binary_transform_result<I0, I1, O> //
0091         RANGES_FUNC(transform)(I0 begin0,
0092                                S0 end0,
0093                                I1 begin1,
0094                                S1 end1,
0095                                O out,
0096                                F fun,
0097                                P0 proj0 = P0{},
0098                                P1 proj1 = P1{}) //
0099         {
0100             for(; begin0 != end0 && begin1 != end1; ++begin0, ++begin1, ++out)
0101                 *out = invoke(fun, invoke(proj0, *begin0), invoke(proj1, *begin1));
0102             return {begin0, begin1, out};
0103         }
0104 
0105         /// \overload
0106         template(typename Rng0,
0107                  typename Rng1,
0108                  typename O,
0109                  typename F,
0110                  typename P0 = identity,
0111                  typename P1 = identity)(
0112             requires input_range<Rng0> AND input_range<Rng1> AND
0113                 weakly_incrementable<O> AND copy_constructible<F> AND
0114                 indirectly_writable<
0115                     O,
0116                     indirect_result_t<F &,
0117                                       projected<iterator_t<Rng0>, P0>,
0118                                       projected<iterator_t<Rng1>, P1>>>)
0119         constexpr binary_transform_result<borrowed_iterator_t<Rng0>,
0120                                           borrowed_iterator_t<Rng1>,
0121                                           O> //
0122         RANGES_FUNC(transform)(
0123             Rng0 && rng0, Rng1 && rng1, O out, F fun, P0 proj0 = P0{}, P1 proj1 = P1{}) //
0124         {
0125             return (*this)(begin(rng0),
0126                            end(rng0),
0127                            begin(rng1),
0128                            end(rng1),
0129                            std::move(out),
0130                            std::move(fun),
0131                            std::move(proj0),
0132                            std::move(proj1));
0133         }
0134 
0135         // Double-range variant, 3-iterator version
0136         /// \overload
0137         template(typename I0,
0138                      typename S0,
0139                      typename I1,
0140                      typename O,
0141                      typename F,
0142                      typename P0 = identity,
0143                      typename P1 = identity)(
0144             requires input_iterator<I0> AND sentinel_for<S0, I0> AND
0145                 input_iterator<I1> AND weakly_incrementable<O> AND
0146                 copy_constructible<F> AND
0147                 indirectly_writable<
0148                     O,
0149                     indirect_result_t<F &, projected<I0, P0>, projected<I1, P1>>>)
0150         RANGES_DEPRECATED(
0151             "Use the variant of ranges::transform that takes an upper bound "
0152             "for both input ranges")
0153         binary_transform_result<I0, I1, O> //
0154         RANGES_FUNC(transform)(I0 begin0,
0155                                S0 end0,
0156                                I1 begin1,
0157                                O out,
0158                                F fun,
0159                                P0 proj0 = P0{},
0160                                P1 proj1 = P1{})
0161         {
0162             return (*this)(std::move(begin0),
0163                            std::move(end0),
0164                            std::move(begin1),
0165                            unreachable,
0166                            std::move(out),
0167                            std::move(fun),
0168                            std::move(proj0),
0169                            std::move(proj1));
0170         }
0171 
0172         /// \overload
0173         template(typename Rng0,
0174                  typename I1Ref,
0175                  typename O,
0176                  typename F,
0177                  typename P0 = identity,
0178                  typename P1 = identity)(
0179             requires input_range<Rng0> AND input_iterator<uncvref_t<I1Ref>> AND
0180                 weakly_incrementable<O> AND copy_constructible<F> AND
0181                 indirectly_writable<
0182                     O,
0183                     indirect_result_t<F &,
0184                                       projected<iterator_t<Rng0>, P0>,
0185                                       projected<uncvref_t<I1Ref>, P1>>>)
0186         RANGES_DEPRECATED(
0187             "Use the variant of ranges::transform that takes an upper bound "
0188             "for both input ranges")
0189         binary_transform_result<borrowed_iterator_t<Rng0>, uncvref_t<I1Ref>, O> //
0190         RANGES_FUNC(transform)(Rng0 && rng0,
0191                                I1Ref && begin1,
0192                                O out,
0193                                F fun,
0194                                P0 proj0 = P0{},
0195                                P1 proj1 = P1{}) //
0196         {
0197             return (*this)(begin(rng0),
0198                            end(rng0),
0199                            static_cast<I1Ref &&>(begin1),
0200                            unreachable,
0201                            std::move(out),
0202                            std::move(fun),
0203                            std::move(proj0),
0204                            std::move(proj1));
0205         }
0206 
0207     RANGES_FUNC_END(transform)
0208 
0209     namespace cpp20
0210     {
0211         using ranges::binary_transform_result;
0212         using ranges::transform;
0213         using ranges::unary_transform_result;
0214     } // namespace cpp20
0215     /// @}
0216 } // namespace ranges
0217 
0218 #include <range/v3/detail/epilogue.hpp>
0219 
0220 #endif