File indexing completed on 2025-09-18 08:47:27
0001
0002
0003
0004
0005
0006
0007 #ifndef BOOST_ITERATOR_TRANSFORM_ITERATOR_23022003THW_HPP
0008 #define BOOST_ITERATOR_TRANSFORM_ITERATOR_23022003THW_HPP
0009
0010 #include <iterator>
0011 #include <type_traits>
0012
0013 #include <boost/core/use_default.hpp>
0014 #include <boost/core/empty_value.hpp>
0015 #include <boost/iterator/iterator_adaptor.hpp>
0016 #include <boost/iterator/enable_if_convertible.hpp>
0017 #include <boost/iterator/detail/eval_if_default.hpp>
0018
0019 namespace boost {
0020 namespace iterators {
0021
0022 template<
0023 typename UnaryFunction,
0024 typename Iterator,
0025 typename Reference = use_default,
0026 typename Value = use_default
0027 >
0028 class transform_iterator;
0029
0030 namespace detail {
0031
0032 template< typename UnaryFunc, typename Iterator >
0033 struct transform_iterator_default_reference
0034 {
0035 using type = decltype(std::declval< UnaryFunc const& >()(std::declval< typename std::iterator_traits< Iterator >::reference >()));
0036 };
0037
0038
0039 template< typename UnaryFunc, typename Iterator, typename Reference, typename Value >
0040 struct transform_iterator_base
0041 {
0042 private:
0043
0044
0045 using reference = detail::eval_if_default_t<
0046 Reference,
0047 transform_iterator_default_reference< UnaryFunc, Iterator >
0048 >;
0049
0050
0051
0052
0053
0054
0055 using cv_value_type = detail::eval_if_default_t<
0056 Value,
0057 std::remove_reference< reference >
0058 >;
0059
0060 public:
0061 using type = iterator_adaptor<
0062 transform_iterator< UnaryFunc, Iterator, Reference, Value >,
0063 Iterator,
0064 cv_value_type,
0065 use_default,
0066 reference
0067 >;
0068 };
0069
0070 }
0071
0072 template< typename UnaryFunc, typename Iterator, typename Reference, typename Value >
0073 class transform_iterator :
0074 public detail::transform_iterator_base< UnaryFunc, Iterator, Reference, Value >::type,
0075 private boost::empty_value< UnaryFunc >
0076 {
0077 friend class iterator_core_access;
0078
0079 private:
0080 using super_t = typename detail::transform_iterator_base< UnaryFunc, Iterator, Reference, Value >::type;
0081 using functor_base = boost::empty_value< UnaryFunc >;
0082
0083 public:
0084 transform_iterator() = default;
0085
0086 transform_iterator(Iterator const& x, UnaryFunc f) :
0087 super_t(x),
0088 functor_base(boost::empty_init_t{}, f)
0089 {}
0090
0091
0092
0093 template< bool Requires = std::is_class< UnaryFunc >::value, typename = typename std::enable_if< Requires >::type >
0094 explicit transform_iterator(Iterator const& x) :
0095 super_t(x)
0096 {}
0097
0098 template<
0099 typename OtherUnaryFunction,
0100 typename OtherIterator,
0101 typename OtherReference,
0102 typename OtherValue,
0103 typename = enable_if_convertible_t< OtherIterator, Iterator >,
0104 typename = enable_if_convertible_t< OtherUnaryFunction, UnaryFunc >
0105 >
0106 transform_iterator(transform_iterator< OtherUnaryFunction, OtherIterator, OtherReference, OtherValue > const& t) :
0107 super_t(t.base()),
0108 functor_base(boost::empty_init_t{}, t.functor())
0109 {}
0110
0111 UnaryFunc functor() const { return functor_base::get(); }
0112
0113 private:
0114 typename super_t::reference dereference() const { return functor_base::get()(*this->base()); }
0115 };
0116
0117 template< typename UnaryFunc, typename Iterator >
0118 inline transform_iterator< UnaryFunc, Iterator > make_transform_iterator(Iterator it, UnaryFunc fun)
0119 {
0120 return transform_iterator< UnaryFunc, Iterator >(it, fun);
0121 }
0122
0123
0124
0125
0126
0127
0128
0129
0130 template< typename UnaryFunc, typename Iterator >
0131 inline typename std::enable_if<
0132 std::is_class< UnaryFunc >::value,
0133 transform_iterator< UnaryFunc, Iterator >
0134 >::type make_transform_iterator(Iterator it)
0135 {
0136 return transform_iterator< UnaryFunc, Iterator >(it);
0137 }
0138
0139 }
0140
0141 using iterators::transform_iterator;
0142 using iterators::make_transform_iterator;
0143
0144 }
0145
0146 #endif