fix support for STL container: some algorithms

This commit is contained in:
bolero-MURAKAMI 2013-01-17 03:53:17 +09:00
parent ace6acad69
commit a9cd556f8e
28 changed files with 911 additions and 106 deletions

View file

@ -7,8 +7,8 @@
#include <sprout/algorithm/fixed/copy.hpp> #include <sprout/algorithm/fixed/copy.hpp>
#include <sprout/algorithm/fit/result_of.hpp> #include <sprout/algorithm/fit/result_of.hpp>
#include <sprout/sub_array.hpp> #include <sprout/sub_array.hpp>
#include HDR_ALGORITHM_SSCRISK_CEL_OR_SPROUT
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include HDR_ALGORITHM_SSCRISK_CEL_OR_SPROUT
namespace sprout { namespace sprout {
namespace fit { namespace fit {

View file

@ -9,6 +9,7 @@
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/pit.hpp>
#include <sprout/math/comparison.hpp> #include <sprout/math/comparison.hpp>
#include <sprout/detail/container_complate.hpp> #include <sprout/detail/container_complate.hpp>
@ -94,18 +95,17 @@ namespace sprout {
sprout::is_fixed_container<Result>::value, sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type typename sprout::fixed::result_of::algorithm<Result>::type
>::type >::type
copy(InputIterator first, InputIterator last, Result const& result) copy(InputIterator first, InputIterator last, Result const& result) {
{
typedef typename std::iterator_traits<InputIterator>::iterator_category* category; typedef typename std::iterator_traits<InputIterator>::iterator_category* category;
return sprout::fixed::detail::copy(first, last, result, category()); return sprout::fixed::detail::copy(first, last, result, category());
} }
template<typename InputIterator, typename Result> template<typename InputIterator, typename Result>
inline SPROUT_CONSTEXPR typename std::enable_if< inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Result>::value, !sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type typename sprout::fixed::result_of::algorithm<Result>::type
>::type >::type
copy(InputIterator first, InputIterator last, Result const& result) copy(InputIterator first, InputIterator last, Result const& result) {
{
return sprout::remake<Result>( return sprout::remake<Result>(
result, result,
sprout::size(result), sprout::size(result),
@ -121,6 +121,12 @@ namespace sprout {
copy(InputIterator first, InputIterator last, Result const& result) { copy(InputIterator first, InputIterator last, Result const& result) {
return sprout::fixed::detail::copy(first, last, result); return sprout::fixed::detail::copy(first, last, result);
} }
template<typename Result, typename InputIterator>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy(InputIterator first, InputIterator last) {
return sprout::fixed::copy(first, last, sprout::pit<Result>());
}
} // namespace fixed } // namespace fixed
using sprout::fixed::copy; using sprout::fixed::copy;

View file

@ -9,6 +9,7 @@
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/pit.hpp>
#include <sprout/math/comparison.hpp> #include <sprout/math/comparison.hpp>
#include <sprout/detail/container_complate_backward.hpp> #include <sprout/detail/container_complate_backward.hpp>
@ -86,12 +87,33 @@ namespace sprout {
) )
{ {
return sprout::fixed::detail::copy_backward_impl( return sprout::fixed::detail::copy_backward_impl(
first, first, last, result,
last,
result,
sprout::size(result) sprout::size(result)
); );
} }
template<typename BidirectionalIterator, typename Result>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
copy_backward(BidirectionalIterator first, BidirectionalIterator last, Result const& result) {
typedef typename std::iterator_traits<BidirectionalIterator>::iterator_category* category;
return sprout::fixed::detail::copy_backward(first, last, result, category());
}
template<typename BidirectionalIterator, typename Result>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
copy_backward(BidirectionalIterator first, BidirectionalIterator last, Result const& result) {
return sprout::remake<Result>(
result,
sprout::size(result),
first, last
);
}
} // namespace detail } // namespace detail
// //
// copy_backward // copy_backward
@ -99,13 +121,13 @@ namespace sprout {
template<typename BidirectionalIterator, typename Result> template<typename BidirectionalIterator, typename Result>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy_backward(BidirectionalIterator first, BidirectionalIterator last, Result const& result) { copy_backward(BidirectionalIterator first, BidirectionalIterator last, Result const& result) {
typedef typename std::iterator_traits<BidirectionalIterator>::iterator_category* category; return sprout::fixed::detail::copy_backward(first, last, result);
return sprout::fixed::detail::copy_backward( }
first,
last, template<typename Result, typename BidirectionalIterator>
result, inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
category() copy_backward(BidirectionalIterator first, BidirectionalIterator last) {
); return sprout::fixed::copy_backward(first, last, sprout::pit<Result>());
} }
} // namespace fixed } // namespace fixed

View file

@ -6,7 +6,9 @@
#include <sprout/container/traits.hpp> #include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include <sprout/iterator/filter_iterator.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/pit.hpp>
#include <sprout/detail/container_complate.hpp> #include <sprout/detail/container_complate.hpp>
namespace sprout { namespace sprout {
@ -42,6 +44,28 @@ namespace sprout {
: sprout::detail::container_complate(result, args...) : sprout::detail::container_complate(result, args...)
; ;
} }
template<typename InputIterator, typename Result, typename Predicate>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
copy_if(InputIterator first, InputIterator last, Result const& result, Predicate pred) {
return sprout::fixed::detail::copy_if_impl(first, last, result, pred, sprout::size(result));
}
template<typename InputIterator, typename Result, typename Predicate>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
copy_if(InputIterator first, InputIterator last, Result const& result, Predicate pred) {
return sprout::remake<Result>(
result,
sprout::size(result),
sprout::make_filter_iterator(pred, first, last), sprout::make_filter_iterator(pred, last, last)
);
}
} // namespace detail } // namespace detail
// //
// copy_if // copy_if
@ -49,7 +73,13 @@ namespace sprout {
template<typename InputIterator, typename Result, typename Predicate> template<typename InputIterator, typename Result, typename Predicate>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy_if(InputIterator first, InputIterator last, Result const& result, Predicate pred) { copy_if(InputIterator first, InputIterator last, Result const& result, Predicate pred) {
return sprout::fixed::detail::copy_if_impl(first, last, result, pred, sprout::size(result)); return sprout::fixed::detail::copy_if(first, last, result, pred);
}
template<typename Result, typename InputIterator, typename Predicate>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy_if(InputIterator first, InputIterator last, Predicate pred) {
return sprout::fixed::copy_if(first, last, sprout::pit<Result>(), pred);
} }
} // namespace fixed } // namespace fixed

View file

@ -9,6 +9,7 @@
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/algorithm/fixed/copy.hpp> #include <sprout/algorithm/fixed/copy.hpp>
#include <sprout/pit.hpp>
#include <sprout/math/comparison.hpp> #include <sprout/math/comparison.hpp>
#include <sprout/detail/container_complate.hpp> #include <sprout/detail/container_complate.hpp>
@ -24,6 +25,7 @@ namespace sprout {
{ {
return sprout::fixed::copy(first, sprout::next(first, n), result); return sprout::fixed::copy(first, sprout::next(first, n), result);
} }
template<typename InputIterator, typename Size, typename Result, typename... Args> template<typename InputIterator, typename Size, typename Result, typename... Args>
inline SPROUT_CONSTEXPR typename std::enable_if< inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::container_traits<Result>::static_size == sizeof...(Args), sprout::container_traits<Result>::static_size == sizeof...(Args),
@ -61,6 +63,35 @@ namespace sprout {
{ {
return sprout::fixed::detail::copy_n_impl(first, n, result, sprout::size(result)); return sprout::fixed::detail::copy_n_impl(first, n, result, sprout::size(result));
} }
template<typename InputIterator, typename Size, typename Result>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
copy_n(InputIterator first, Size n, Result const& result) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category;
return sprout::fixed::detail::copy_n(first, n, result, category());
}
template<typename ForwardIterator, typename Size, typename Result>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy_n_dyn(
ForwardIterator first, Size n, Result const& result,
std::forward_iterator_tag*
)
{
return sprout::fixed::copy(first, sprout::next(first, n), result);
}
template<typename InputIterator, typename Size, typename Result>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
copy_n(InputIterator first, Size n, Result const& result) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category;
return sprout::fixed::detail::copy_n_dyn(first, n, result, category());
}
} // namespace detail } // namespace detail
// //
// copy_n // copy_n
@ -68,8 +99,13 @@ namespace sprout {
template<typename InputIterator, typename Size, typename Result> template<typename InputIterator, typename Size, typename Result>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy_n(InputIterator first, Size n, Result const& result) { copy_n(InputIterator first, Size n, Result const& result) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category; return sprout::fixed::detail::copy_n(first, n, result);
return sprout::fixed::detail::copy_n(first, n, result, category()); }
template<typename Result, typename InputIterator, typename Size>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy_n(InputIterator first, Size n) {
return sprout::fixed::copy_n(first, n, sprout::pit<Result>());
} }
} // namespace fixed } // namespace fixed

View file

@ -6,6 +6,7 @@
#include <sprout/container/traits.hpp> #include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include <sprout/iterator/value_iterator.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
namespace sprout { namespace sprout {
@ -29,6 +30,33 @@ namespace sprout {
)... )...
); );
} }
template<typename Container, typename T>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Container>::value,
typename sprout::fixed::result_of::algorithm<Container>::type
>::type
fill(Container const& cont, T const& value) {
return sprout::fixed::detail::fill_impl(
cont, value,
sprout::index_range<0, sprout::container_traits<Container>::static_size>::make(),
sprout::internal_begin_offset(cont),
sprout::size(cont)
);
}
template<typename Container, typename T>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Container>::value,
typename sprout::fixed::result_of::algorithm<Container>::type
>::type
fill(Container const& cont, T const& value) {
return sprout::remake<Container>(
cont,
sprout::size(cont),
sprout::value_iterator<T const&>(value), sprout::value_iterator<T const&>(value, 0)
);
}
} // namespace detail } // namespace detail
// //
// fill // fill
@ -36,12 +64,7 @@ namespace sprout {
template<typename Container, typename T> template<typename Container, typename T>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Container>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Container>::type
fill(Container const& cont, T const& value) { fill(Container const& cont, T const& value) {
return sprout::fixed::detail::fill_impl( return sprout::fixed::detail::fill(cont, value);
cont, value,
sprout::index_range<0, sprout::container_traits<Container>::static_size>::make(),
sprout::internal_begin_offset(cont),
sprout::size(cont)
);
} }
} // namespace fixed } // namespace fixed

View file

@ -10,18 +10,41 @@
namespace sprout { namespace sprout {
namespace fixed { namespace fixed {
namespace detail {
template<typename Container, typename Size, typename T>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Container>::value,
typename sprout::fixed::result_of::algorithm<Container>::type
>::type
fill_n(Container const& cont, Size n, T const& value) {
return sprout::fixed::detail::fill_impl(
cont, value,
sprout::index_range<0, sprout::container_traits<Container>::static_size>::make(),
sprout::internal_begin_offset(cont),
n
);
}
template<typename Container, typename Size, typename T>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Container>::value,
typename sprout::fixed::result_of::algorithm<Container>::type
>::type
fill_n(Container const& cont, Size n, T const& value) {
return sprout::remake<Container>(
cont,
n,
sprout::value_iterator<T const&>(value, n), sprout::value_iterator<T const&>(value, 0)
);
}
} // namespace detail
// //
// fill_n // fill_n
// //
template<typename Container, typename Size, typename T> template<typename Container, typename Size, typename T>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Container>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Container>::type
fill_n(Container const& cont, Size n, T const& value) { fill_n(Container const& cont, Size n, T const& value) {
return sprout::fixed::detail::fill_impl( return sprout::fixed::detail::fill_n(cont, n, value);
cont, value,
sprout::index_range<0, sprout::container_traits<Container>::static_size>::make(),
sprout::internal_begin_offset(cont),
n
);
} }
} // namespace fixed } // namespace fixed

View file

@ -8,7 +8,9 @@
#include <sprout/container/traits.hpp> #include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include <sprout/iterator/replace_iterator.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/pit.hpp>
#include <sprout/detail/container_complate.hpp> #include <sprout/detail/container_complate.hpp>
#include HDR_FUNCTIONAL_SSCRISK_CEL_OR_SPROUT #include HDR_FUNCTIONAL_SSCRISK_CEL_OR_SPROUT
@ -97,6 +99,30 @@ namespace sprout {
{ {
return sprout::fixed::detail::replace_copy_impl(first, last, result, old_value, new_value, sprout::size(result)); return sprout::fixed::detail::replace_copy_impl(first, last, result, old_value, new_value, sprout::size(result));
} }
template<typename InputIterator, typename Result, typename T>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
replace_copy(InputIterator first, InputIterator last, Result const& result, T const& old_value, T const& new_value) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category;
return sprout::fixed::detail::replace_copy(first, last, result, old_value, new_value, category());
}
template<typename InputIterator, typename Result, typename T>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
replace_copy(InputIterator first, InputIterator last, Result const& result, T const& old_value, T const& new_value) {
return sprout::remake<Result>(
result,
sprout::size(result),
sprout::make_replace_iterator(first, old_value, new_value),
sprout::make_replace_iterator(last, old_value, new_value)
);
}
} // namespace detail } // namespace detail
// //
// replace_copy // replace_copy
@ -104,8 +130,13 @@ namespace sprout {
template<typename InputIterator, typename Result, typename T> template<typename InputIterator, typename Result, typename T>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
replace_copy(InputIterator first, InputIterator last, Result const& result, T const& old_value, T const& new_value) { replace_copy(InputIterator first, InputIterator last, Result const& result, T const& old_value, T const& new_value) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category; return sprout::fixed::detail::replace_copy(first, last, result, old_value, new_value);
return sprout::fixed::detail::replace_copy(first, last, result, old_value, new_value, category()); }
template<typename Result, typename InputIterator, typename T>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
replace_copy(InputIterator first, InputIterator last, T const& old_value, T const& new_value) {
return sprout::fixed::replace_copy(first, last, sprout::pit<Result>(), old_value, new_value);
} }
} // namespace fixed } // namespace fixed

View file

@ -8,7 +8,9 @@
#include <sprout/container/traits.hpp> #include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include <sprout/iterator/replace_if_iterator.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/pit.hpp>
#include <sprout/detail/container_complate.hpp> #include <sprout/detail/container_complate.hpp>
namespace sprout { namespace sprout {
@ -96,6 +98,30 @@ namespace sprout {
{ {
return sprout::fixed::detail::replace_copy_if_impl(first, last, result, pred, new_value, sprout::size(result)); return sprout::fixed::detail::replace_copy_if_impl(first, last, result, pred, new_value, sprout::size(result));
} }
template<typename InputIterator, typename Result, typename T, typename Predicate>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
replace_copy_if(InputIterator first, InputIterator last, Result const& result, Predicate pred, T const& new_value) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category;
return sprout::fixed::detail::replace_copy_if(first, last, result, pred, new_value, category());
}
template<typename InputIterator, typename Result, typename T, typename Predicate>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
replace_copy_if(InputIterator first, InputIterator last, Result const& result, Predicate pred, T const& new_value) {
return sprout::remake<Result>(
result,
sprout::size(result),
sprout::make_replace_if_iterator(first, pred, new_value),
sprout::make_replace_if_iterator(last, pred, new_value)
);
}
} // namespace detail } // namespace detail
// //
// replace_copy_if // replace_copy_if
@ -103,8 +129,13 @@ namespace sprout {
template<typename InputIterator, typename Result, typename T, typename Predicate> template<typename InputIterator, typename Result, typename T, typename Predicate>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
replace_copy_if(InputIterator first, InputIterator last, Result const& result, Predicate pred, T const& new_value) { replace_copy_if(InputIterator first, InputIterator last, Result const& result, Predicate pred, T const& new_value) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category; return sprout::fixed::detail::replace_copy_if(first, last, result, pred, new_value);
return sprout::fixed::detail::replace_copy_if(first, last, result, pred, new_value, category()); }
template<typename Result, typename InputIterator, typename T, typename Predicate>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
replace_copy_if(InputIterator first, InputIterator last, Predicate pred, T const& new_value) {
return sprout::fixed::replace_copy_if(first, last, sprout::pit<Result>(), pred, new_value);
} }
} // namespace fixed } // namespace fixed

View file

@ -8,7 +8,10 @@
#include <sprout/container/traits.hpp> #include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/operation.hpp> #include <sprout/iterator/operation.hpp>
#include <sprout/iterator/transform_iterator.hpp>
#include <sprout/iterator/type_traits/common.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/pit.hpp>
#include <sprout/detail/container_complate.hpp> #include <sprout/detail/container_complate.hpp>
namespace sprout { namespace sprout {
@ -51,6 +54,7 @@ namespace sprout {
sprout::distance(first, last) sprout::distance(first, last)
); );
} }
template<typename InputIterator, typename Result, typename UnaryOperation, typename... Args> template<typename InputIterator, typename Result, typename UnaryOperation, typename... Args>
inline SPROUT_CONSTEXPR typename std::enable_if< inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::container_traits<Result>::static_size == sizeof...(Args), sprout::container_traits<Result>::static_size == sizeof...(Args),
@ -92,6 +96,29 @@ namespace sprout {
{ {
return sprout::fixed::detail::transform_impl(first, last, result, op, sprout::size(result)); return sprout::fixed::detail::transform_impl(first, last, result, op, sprout::size(result));
} }
template<typename InputIterator, typename Result, typename UnaryOperation>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
transform(InputIterator first, InputIterator last, Result const& result, UnaryOperation op) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category;
return sprout::fixed::detail::transform(first, last, result, op, category());
}
template<typename InputIterator, typename Result, typename UnaryOperation>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
transform(InputIterator first, InputIterator last, Result const& result, UnaryOperation op) {
return sprout::remake<Result>(
result,
sprout::size(result),
sprout::make_transform_iterator(first, op), sprout::make_transform_iterator(last, op)
);
}
} // namespace detail } // namespace detail
// //
// transform // transform
@ -99,8 +126,13 @@ namespace sprout {
template<typename InputIterator, typename Result, typename UnaryOperation> template<typename InputIterator, typename Result, typename UnaryOperation>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
transform(InputIterator first, InputIterator last, Result const& result, UnaryOperation op) { transform(InputIterator first, InputIterator last, Result const& result, UnaryOperation op) {
typedef typename std::iterator_traits<InputIterator>::iterator_category* category; return sprout::fixed::detail::transform(first, last, result, op);
return sprout::fixed::detail::transform(first, last, result, op, category()); }
template<typename Result, typename InputIterator, typename UnaryOperation>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
transform(InputIterator first, InputIterator last, UnaryOperation op) {
return sprout::fixed::transform(first, last, sprout::pit<Result>(), op);
} }
namespace detail { namespace detail {
@ -182,6 +214,30 @@ namespace sprout {
{ {
return sprout::fixed::detail::transform_impl(first1, last1, first2, result, op, sprout::size(result)); return sprout::fixed::detail::transform_impl(first1, last1, first2, result, op, sprout::size(result));
} }
template<typename InputIterator1, typename InputIterator2, typename Result, typename BinaryOperation>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
transform(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, Result const& result, BinaryOperation op) {
typedef typename sprout::common_iterator_category<InputIterator1, InputIterator2>::type* category;
return sprout::fixed::detail::transform(first1, last1, first2, result, op, category());
}
template<typename InputIterator1, typename InputIterator2, typename Result, typename BinaryOperation>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Result>::value,
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
transform(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, Result const& result, BinaryOperation op) {
return sprout::remake<Result>(
result,
sprout::size(result),
sprout::make_transform_iterator(first1, first2, op),
sprout::make_transform_iterator(last1, first2, op)
);
}
} // namespace detail } // namespace detail
// //
// transform // transform
@ -189,8 +245,13 @@ namespace sprout {
template<typename InputIterator1, typename InputIterator2, typename Result, typename BinaryOperation> template<typename InputIterator1, typename InputIterator2, typename Result, typename BinaryOperation>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
transform(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, Result const& result, BinaryOperation op) { transform(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, Result const& result, BinaryOperation op) {
typedef typename std::iterator_traits<InputIterator1>::iterator_category* category; return sprout::fixed::detail::transform(first1, last1, first2, result, op);
return sprout::fixed::detail::transform(first1, last1, first2, result, op, category()); }
template<typename Result, typename InputIterator1, typename InputIterator2, typename BinaryOperation>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
transform(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, BinaryOperation op) {
return sprout::fixed::transform(first1, last1, first2, sprout::pit<Result>(), op);
} }
} // namespace fixed } // namespace fixed

View file

@ -4,6 +4,13 @@
#include <type_traits> #include <type_traits>
#include <sprout/config.hpp> #include <sprout/config.hpp>
#include <sprout/container/container_traits.hpp> #include <sprout/container/container_traits.hpp>
#include <sprout/container/internal_begin.hpp>
#include <sprout/container/internal_end.hpp>
#include <sprout/container/internal_begin_offset.hpp>
#include <sprout/container/internal_end_offset.hpp>
#include <sprout/container/internal_begin_offset_backward.hpp>
#include <sprout/container/internal_end_offset_backward.hpp>
#include <sprout/iterator/remake_iterator.hpp>
#include <sprout/utility/forward.hpp> #include <sprout/utility/forward.hpp>
namespace sprout { namespace sprout {
@ -33,6 +40,43 @@ namespace sprout {
return copied_type{sprout::forward<Args>(args)...}; return copied_type{sprout::forward<Args>(args)...};
} }
template<typename Container, typename Cont, typename... Args>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::is_fixed_container<Container>::value,
typename sprout::container_construct_traits<Container>::copied_type
>::type
default_remake_container(Cont&& cont, typename sprout::container_traits<Container>::difference_type size, Args&&... args) {
return sprout::container_construct_traits<Container>::make(sprout::forward<Args>(args)...);
}
template<typename Container, typename Cont, typename... Args>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Container>::value,
typename sprout::container_construct_traits<Container>::copied_type
>::type
default_remake_container(Cont&& cont, typename sprout::container_traits<Container>::difference_type size, Args&&... args) {
return sprout::container_construct_traits<Container>::make(sprout::forward<Args>(args)...);
}
template<typename Container, typename Cont, typename InputIterator>
inline SPROUT_CONSTEXPR typename std::enable_if<
!sprout::is_fixed_container<Container>::value,
typename sprout::container_construct_traits<Container>::copied_type
>::type
default_remake_container(Cont&& cont, typename sprout::container_traits<Container>::difference_type size, InputIterator first, InputIterator last) {
typedef typename sprout::container_construct_traits<Container>::copied_type copied_type;
return copied_type(
sprout::make_remake_iterator(
sprout::internal_begin(cont), first,
first, last,
sprout::internal_begin_offset(cont), sprout::internal_end_offset(cont)
),
sprout::make_remake_iterator(
sprout::internal_end(cont), last,
first, last,
sprout::internal_begin_offset_backward(cont), sprout::internal_end_offset_backward(cont)
)
);
}
template<typename Container> template<typename Container>
struct container_construct_traits_impl { struct container_construct_traits_impl {
public: public:
@ -51,7 +95,10 @@ namespace sprout {
template<typename Cont, typename... Args> template<typename Cont, typename... Args>
static SPROUT_CONSTEXPR copied_type static SPROUT_CONSTEXPR copied_type
remake(Cont&& cont, typename sprout::container_traits<Container>::difference_type size, Args&&... args) { remake(Cont&& cont, typename sprout::container_traits<Container>::difference_type size, Args&&... args) {
return make(sprout::forward<Args>(args)...); return sprout::detail::default_remake_container<Container>(
sprout::forward<Cont>(cont), size,
sprout::forward<Args>(args)...
);
} }
}; };
} // namespace detail } // namespace detail

View file

@ -13,6 +13,7 @@
#include <sprout/container/get_internal.hpp> #include <sprout/container/get_internal.hpp>
#include <sprout/container/internal_begin.hpp> #include <sprout/container/internal_begin.hpp>
#include <sprout/container/internal_end.hpp> #include <sprout/container/internal_end.hpp>
#include <sprout/container/internal_size.hpp>
#include <sprout/container/internal_begin_offset.hpp> #include <sprout/container/internal_begin_offset.hpp>
#include <sprout/container/internal_end_offset.hpp> #include <sprout/container/internal_end_offset.hpp>
#include <sprout/container/internal_begin_offset_backward.hpp> #include <sprout/container/internal_begin_offset_backward.hpp>

View file

@ -0,0 +1,21 @@
#ifndef SPROUT_CONTAINER_INTERNAL_SIZE_HPP
#define SPROUT_CONTAINER_INTERNAL_SIZE_HPP
#include <sprout/config.hpp>
#include <sprout/container/container_traits.hpp>
#include <sprout/container/internal_begin.hpp>
#include <sprout/container/internal_end.hpp>
#include <sprout/iterator/operation.hpp>
namespace sprout {
//
// internal_size
//
template<typename Container>
inline SPROUT_CONSTEXPR typename sprout::container_traits<Container>::difference_type
internal_size(Container const& cont) {
return sprout::distance(sprout::internal_begin(cont), sprout::internal_end(cont));
}
} // namespace sprout
#endif // #ifndef SPROUT_CONTAINER_INTERNAL_SIZE_HPP

View file

@ -4,6 +4,8 @@
#include <sprout/config.hpp> #include <sprout/config.hpp>
#include <sprout/iterator/reverse_iterator.hpp> #include <sprout/iterator/reverse_iterator.hpp>
#include <sprout/iterator/transform_iterator.hpp> #include <sprout/iterator/transform_iterator.hpp>
#include <sprout/iterator/replace_iterator.hpp>
#include <sprout/iterator/replace_if_iterator.hpp>
#include <sprout/iterator/filter_iterator.hpp> #include <sprout/iterator/filter_iterator.hpp>
#include <sprout/iterator/step_iterator.hpp> #include <sprout/iterator/step_iterator.hpp>
#include <sprout/iterator/indexed_iterator.hpp> #include <sprout/iterator/indexed_iterator.hpp>
@ -12,5 +14,6 @@
#include <sprout/iterator/alternate_iterator.hpp> #include <sprout/iterator/alternate_iterator.hpp>
#include <sprout/iterator/size_enum_iterator.hpp> #include <sprout/iterator/size_enum_iterator.hpp>
#include <sprout/iterator/bytes_iterator.hpp> #include <sprout/iterator/bytes_iterator.hpp>
#include <sprout/iterator/remake_iterator.hpp>
#endif // #ifndef SPROUT_ITERATOR_ADAPTOR_HPP #endif // #ifndef SPROUT_ITERATOR_ADAPTOR_HPP

View file

@ -0,0 +1,343 @@
#ifndef SPROUT_ITERATOR_REMAKE_ITERATOR_HPP
#define SPROUT_ITERATOR_REMAKE_ITERATOR_HPP
#include <iterator>
#include <utility>
#include <sprout/config.hpp>
#include <sprout/iterator/next.hpp>
#include <sprout/iterator/prev.hpp>
#include <sprout/iterator/distance.hpp>
#include <sprout/iterator/type_traits/common.hpp>
#include <sprout/utility/swap.hpp>
#include HDR_ALGORITHM_SSCRISK_CEL_OR_SPROUT
namespace sprout {
//
// remake_iterator
//
template<typename DstIterator, typename SrcIterator>
class remake_iterator
: public std::iterator<
typename sprout::common_iterator_category<DstIterator, SrcIterator>::type,
typename sprout::common_iterator_value_type<DstIterator, SrcIterator>::type,
typename sprout::common_iterator_difference_type<DstIterator, SrcIterator>::type,
typename sprout::common_iterator_pointer<DstIterator, SrcIterator>::type,
typename sprout::common_iterator_reference<DstIterator, SrcIterator>::type
>
{
public:
typedef DstIterator iterator_type;
typedef SrcIterator iterator2_type;
typedef typename sprout::common_iterator_category<DstIterator, SrcIterator>::type iterator_category;
typedef typename sprout::common_iterator_value_type<DstIterator, SrcIterator>::type value_type;
typedef typename sprout::common_iterator_difference_type<DstIterator, SrcIterator>::type difference_type;
typedef typename sprout::common_iterator_pointer<DstIterator, SrcIterator>::type pointer;
typedef typename sprout::common_iterator_reference<DstIterator, SrcIterator>::type reference;
private:
SPROUT_CONSTEXPR remake_iterator advance_impl(difference_type n) const {
return n >= 0
? remake_iterator(
sprout::next(current, n),
begin_off - n >= 0 ? fst
: (end_off - begin_off >= sprout::distance(fst, lst) && begin_off - n <= -sprout::distance(fst, lst)) ? lst
: begin_off <= 0
? sprout::next(current2, NS_SSCRISK_CEL_OR_SPROUT::min(NS_SSCRISK_CEL_OR_SPROUT::min(n, end_off), sprout::distance(current2, lst)))
: sprout::next(current2, NS_SSCRISK_CEL_OR_SPROUT::min(NS_SSCRISK_CEL_OR_SPROUT::min(n - begin_off, end_off), sprout::distance(current2, lst)))
,
fst, lst,
begin_off - n, end_off - n
)
: remake_iterator(
sprout::next(current, n),
begin_off - n >= 0 ? fst
: (end_off - begin_off >= sprout::distance(fst, lst) && begin_off - n <= -sprout::distance(fst, lst)) ? lst
: begin_off >= -sprout::distance(fst, lst)
? sprout::next(current2, n)
: sprout::next(current2, n - (begin_off + sprout::distance(fst, lst)))
,
fst, lst,
begin_off - n, end_off - n
)
;
}
protected:
iterator_type current;
iterator2_type current2;
iterator2_type fst;
iterator2_type lst;
difference_type begin_off;
difference_type end_off;
public:
remake_iterator() = default;
SPROUT_CONSTEXPR remake_iterator(remake_iterator const& other)
: current(other.current), current2(other.current2)
, fst(other.fst) , lst(other.lst)
, begin_off(other.begin_off) , end_off(other.end_off)
{}
SPROUT_CONSTEXPR remake_iterator(iterator_type it, iterator2_type it2, iterator2_type fst, iterator2_type lst, difference_type begin_off, difference_type end_off)
: current(it), current2(it2)
, fst(fst), lst(lst)
, begin_off(begin_off) , end_off(end_off)
{}
template<typename U, typename V>
SPROUT_CONSTEXPR remake_iterator(remake_iterator<U, V> const& it)
: current(it.base()), current2(it.base2())
, fst(it.first()), lst(it.last())
, begin_off(it.begin_offset()) , end_off(it.end_offset())
{}
template<typename U, typename V>
remake_iterator& operator=(remake_iterator<U, V> const& it) {
remake_iterator temp(it);
temp.swap(*this);
return *this;
}
SPROUT_CONSTEXPR iterator_type base() const {
return current;
}
SPROUT_CONSTEXPR iterator2_type base2() const {
return current2;
}
SPROUT_CONSTEXPR iterator2_type first() const {
return fst;
}
SPROUT_CONSTEXPR iterator2_type last() const {
return lst;
}
SPROUT_CONSTEXPR difference_type begin_offset() const {
return begin_off;
}
SPROUT_CONSTEXPR difference_type end_offset() const {
return end_off;
}
SPROUT_CONSTEXPR bool is_in_copying() const {
return begin_off <= 0 && end_off > 0 && current2 != lst;
}
SPROUT_CONSTEXPR reference operator*() const {
return is_in_copying() ? *current2 : *current;
}
SPROUT_CONSTEXPR pointer operator->() const {
return &*(*this);
}
remake_iterator& operator++() {
++current;
if (is_in_copying()) {
++current2;
}
--begin_off;
--end_off;
return *this;
}
remake_iterator operator++(int) {
remake_iterator result(*this);
++current;
if (is_in_copying()) {
++current2;
}
--begin_off;
--end_off;
return result;
}
remake_iterator& operator--() {
--current;
if (begin_off < 0 && end_off >= 0) {
--current2;
}
++begin_off;
++end_off;
return *this;
}
remake_iterator operator--(int) {
remake_iterator temp(*this);
--current;
if (begin_off < 0 && end_off >= 0) {
--current2;
}
++begin_off;
++end_off;
return temp;
}
SPROUT_CONSTEXPR remake_iterator operator+(difference_type n) const {
return advance_impl(n);
}
SPROUT_CONSTEXPR remake_iterator operator-(difference_type n) const {
return advance_impl(-n);
}
remake_iterator& operator+=(difference_type n) {
remake_iterator temp(*this + n);
temp.swap(*this);
return *this;
}
remake_iterator& operator-=(difference_type n) {
remake_iterator temp(*this - n);
temp.swap(*this);
return *this;
}
SPROUT_CONSTEXPR reference operator[](difference_type n) const {
return *(*this + n);
}
SPROUT_CONSTEXPR remake_iterator next() const {
return remake_iterator(
sprout::next(current), (is_in_copying() ? sprout::next(current2) : current2),
fst, last,
begin_off - 1, end_off - 1
);
}
SPROUT_CONSTEXPR remake_iterator prev() const {
return remake_iterator(
sprout::prev(current), (begin_off < 0 && end_off >= 0 ? sprout::prev(current2) : current2),
fst, last,
begin_off + 1, end_off + 1
);
}
void swap(remake_iterator& other)
SPROUT_NOEXCEPT_EXPR(
SPROUT_NOEXCEPT_EXPR(swap(current, other.current))
&& SPROUT_NOEXCEPT_EXPR(swap(current2, other.current2))
&& SPROUT_NOEXCEPT_EXPR(swap(fst, other.fst))
&& SPROUT_NOEXCEPT_EXPR(swap(lst, other.lst))
&& SPROUT_NOEXCEPT_EXPR(swap(begin_off, other.begin_off))
&& SPROUT_NOEXCEPT_EXPR(swap(end_off, other.end_off))
)
{
swap(current, other.current);
swap(current2, other.current2);
swap(fst, other.fst);
swap(lst, other.lst);
swap(begin_off, other.begin_off);
swap(end_off, other.end_off);
}
};
template<
typename DstIterator1, typename SrcIterator1,
typename DstIterator2, typename SrcIterator2
>
inline SPROUT_CONSTEXPR bool operator==(
sprout::remake_iterator<DstIterator1, SrcIterator1> const& lhs,
sprout::remake_iterator<DstIterator2, SrcIterator2> const& rhs
)
{
return lhs.base() == rhs.base();
}
template<
typename DstIterator1, typename SrcIterator1,
typename DstIterator2, typename SrcIterator2
>
inline SPROUT_CONSTEXPR bool operator!=(
sprout::remake_iterator<DstIterator1, SrcIterator1> const& lhs,
sprout::remake_iterator<DstIterator2, SrcIterator2> const& rhs
)
{
return !(lhs == rhs);
}
template<
typename DstIterator1, typename SrcIterator1,
typename DstIterator2, typename SrcIterator2
>
inline SPROUT_CONSTEXPR bool operator<(
sprout::remake_iterator<DstIterator1, SrcIterator1> const& lhs,
sprout::remake_iterator<DstIterator2, SrcIterator2> const& rhs
)
{
return lhs.base() < rhs.base();
}
template<
typename DstIterator1, typename SrcIterator1,
typename DstIterator2, typename SrcIterator2
>
inline SPROUT_CONSTEXPR bool operator>(
sprout::remake_iterator<DstIterator1, SrcIterator1> const& lhs,
sprout::remake_iterator<DstIterator2, SrcIterator2> const& rhs
)
{
return rhs < lhs;
}
template<
typename DstIterator1, typename SrcIterator1,
typename DstIterator2, typename SrcIterator2
>
inline SPROUT_CONSTEXPR bool operator<=(
sprout::remake_iterator<DstIterator1, SrcIterator1> const& lhs,
sprout::remake_iterator<DstIterator2, SrcIterator2> const& rhs
)
{
return !(rhs < lhs);
}
template<
typename DstIterator1, typename SrcIterator1,
typename DstIterator2, typename SrcIterator2
>
inline SPROUT_CONSTEXPR bool operator>=(
sprout::remake_iterator<DstIterator1, SrcIterator1> const& lhs,
sprout::remake_iterator<DstIterator2, SrcIterator2> const& rhs
)
{
return !(lhs < rhs);
}
template<
typename DstIterator1, typename SrcIterator1,
typename DstIterator2, typename SrcIterator2
>
inline SPROUT_CONSTEXPR decltype(std::declval<DstIterator1>() - std::declval<DstIterator2>())
operator-(
sprout::remake_iterator<DstIterator1, SrcIterator1> const& lhs,
sprout::remake_iterator<DstIterator2, SrcIterator2> const& rhs
)
{
return lhs.base() - rhs.base();
}
template<typename DstIterator, typename SrcIterator>
inline SPROUT_CONSTEXPR sprout::remake_iterator<DstIterator, SrcIterator> operator+(
typename sprout::remake_iterator<DstIterator, SrcIterator>::difference_type n,
sprout::remake_iterator<DstIterator, SrcIterator> const& it
)
{
return it + n;
}
//
// make_remake_iterator
//
template<typename DstIterator, typename SrcIterator>
inline SPROUT_CONSTEXPR sprout::remake_iterator<DstIterator, SrcIterator>
make_remake_iterator(
DstIterator it, SrcIterator it2,
SrcIterator fst, SrcIterator lst,
typename sprout::remake_iterator<DstIterator, SrcIterator>::difference_type begin_off,
typename sprout::remake_iterator<DstIterator, SrcIterator>::difference_type end_off
)
{
return sprout::remake_iterator<DstIterator, SrcIterator>(it, it2, fst, lst, begin_off, end_off);
}
//
// swap
//
template<typename DstIterator, typename SrcIterator>
inline void
swap(sprout::remake_iterator<DstIterator, SrcIterator>& lhs, sprout::remake_iterator<DstIterator, SrcIterator>& rhs)
SPROUT_NOEXCEPT_EXPR(SPROUT_NOEXCEPT_EXPR(lhs.swap(rhs)))
{
lhs.swap(rhs);
}
//
// iterator_next
//
template<typename DstIterator, typename SrcIterator>
inline SPROUT_CONSTEXPR sprout::remake_iterator<DstIterator, SrcIterator>
iterator_next(sprout::remake_iterator<DstIterator, SrcIterator> const& it) {
return it.next();
}
//
// iterator_prev
//
template<typename DstIterator, typename SrcIterator>
inline SPROUT_CONSTEXPR sprout::remake_iterator<DstIterator, SrcIterator>
iterator_prev(sprout::remake_iterator<DstIterator, SrcIterator> const& it) {
return it.prev();
}
} // namespace sprout
#endif // #ifndef SPROUT_ITERATOR_REMAKE_ITERATOR_HPP

View file

@ -0,0 +1,42 @@
#ifndef SPROUT_ITERATOR_REPLACE_ITERATOR_HPP
#define SPROUT_ITERATOR_REPLACE_ITERATOR_HPP
#include <sprout/config.hpp>
#include <sprout/iterator/transform_iterator.hpp>
namespace sprout {
//
// replace_value_if
//
template<typename Predicate, typename T>
class replace_value_if {
public:
typedef Predicate predicate_type;
typedef T const& result_type;
typedef T const& argument_type;
private:
Predicate pred_;
T new_;
public:
SPROUT_CONSTEXPR replace_value_if(Predicate pred, T const& new_value)
: pred_(pred)
, new_(new_value)
{}
SPROUT_CONSTEXPR T operator()(T const& value) const {
return pred_(value) ? new_ : value;
}
};
//
// make_replace_if_iterator
//
template<typename Predicate, typename T, typename Iterator>
inline SPROUT_CONSTEXPR sprout::transform_iterator<sprout::replace_value_if<Predicate, T>, Iterator>
make_replace_if_iterator(Iterator it, Predicate pred, T const& new_value) {
return sprout::transform_iterator<sprout::replace_value_if<Predicate, T>, Iterator>(
it, sprout::replace_value_if<Predicate, T>(pred, new_value)
);
}
} // namespace sprout
#endif // #ifndef SPROUT_ITERATOR_REPLACE_ITERATOR_HPP

View file

@ -0,0 +1,41 @@
#ifndef SPROUT_ITERATOR_REPLACE_IF_ITERATOR_HPP
#define SPROUT_ITERATOR_REPLACE_IF_ITERATOR_HPP
#include <sprout/config.hpp>
#include <sprout/iterator/transform_iterator.hpp>
namespace sprout {
//
// replace_value
//
template<typename T>
class replace_value {
public:
typedef T const& result_type;
typedef T const& argument_type;
private:
T old_;
T new_;
public:
SPROUT_CONSTEXPR replace_value(T const& old_value, T const& new_value)
: old_(old_value)
, new_(new_value)
{}
SPROUT_CONSTEXPR T operator()(T const& value) const {
return (value == old_) ? new_ : value;
}
};
//
// make_replace_iterator
//
template<typename T, typename Iterator>
inline SPROUT_CONSTEXPR sprout::transform_iterator<sprout::replace_value<T>, Iterator>
make_replace_iterator(Iterator it, T const& old_value, T const& new_value) {
return sprout::transform_iterator<sprout::replace_value<T>, Iterator>(
it, sprout::replace_value<T>(old_value, new_value)
);
}
} // namespace sprout
#endif // #ifndef SPROUT_ITERATOR_REPLACE_IF_ITERATOR_HPP

View file

@ -8,30 +8,72 @@
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
namespace sprout { namespace sprout {
namespace detail {
template<typename Container, typename = void>
struct pit_container_construct_traits;
template<typename Container>
struct pit_container_construct_traits<
sprout::pit<Container>,
typename std::enable_if<sprout::is_fixed_container<Container>::value>::type
> {
public:
typedef typename sprout::container_construct_traits<Container>::copied_type copied_type;
public:
template<typename Cont>
static SPROUT_CONSTEXPR copied_type
deep_copy(Cont&& cont) {
return copied_type();
}
template<typename... Args>
static SPROUT_CONSTEXPR copied_type
make(Args&&... args) {
return sprout::make<copied_type>(sprout::forward<Args>(args)...);
}
template<typename Cont, typename... Args>
static SPROUT_CONSTEXPR copied_type
remake(Cont&& cont, typename sprout::container_traits<sprout::pit<Container> >::difference_type size, Args&&... args) {
return sprout::remake<copied_type>(sprout::forward<Cont>(cont), size, sprout::forward<Args>(args)...);
}
};
template<typename Container>
struct pit_container_construct_traits<
sprout::pit<Container>,
typename std::enable_if<!sprout::is_fixed_container<Container>::value>::type
> {
public:
typedef typename sprout::container_construct_traits<Container>::copied_type copied_type;
public:
template<typename Cont>
static SPROUT_CONSTEXPR copied_type
deep_copy(Cont&& cont) {
return copied_type();
}
template<typename... Args>
static SPROUT_CONSTEXPR copied_type
make(Args&&... args) {
return sprout::make<copied_type>(sprout::forward<Args>(args)...);
}
template<typename Cont, typename... Args>
static SPROUT_CONSTEXPR copied_type
remake(Cont&& cont, typename sprout::container_traits<sprout::pit<Container> >::difference_type size, Args&&... args) {
return sprout::remake<copied_type>(sprout::forward<Cont>(cont), size, sprout::forward<Args>(args)...);
}
template<typename Cont, typename InputIterator>
static SPROUT_CONSTEXPR copied_type
remake(Cont&& cont, typename sprout::container_traits<sprout::pit<Container> >::difference_type size, InputIterator first, InputIterator last) {
return copied_type(first, last);
}
};
} // namespace detail
// //
// container_construct_traits // container_construct_traits
// //
template<typename Container> template<typename Container>
struct container_construct_traits<sprout::pit<Container> > { struct container_construct_traits<sprout::pit<Container> >
public: : public sprout::detail::pit_container_construct_traits<sprout::pit<Container> >
typedef typename sprout::container_construct_traits<Container>::copied_type copied_type; {};
public:
template<typename Cont>
static SPROUT_CONSTEXPR copied_type
deep_copy(Cont&& cont) {
return copied_type();
}
template<typename... Args>
static SPROUT_CONSTEXPR copied_type
make(Args&&... args) {
return sprout::make<copied_type>(sprout::forward<Args>(args)...);
}
template<typename Cont, typename... Args>
static SPROUT_CONSTEXPR copied_type
remake(Cont&& cont, typename sprout::container_traits<sprout::pit<Container> >::difference_type size, Args&&... args) {
return sprout::remake<copied_type>(sprout::forward<Cont>(cont), size, sprout::forward<Args>(args)...);
}
};
// //
// container_transform_traits // container_transform_traits

View file

@ -3,7 +3,6 @@
#include <type_traits> #include <type_traits>
#include <sprout/config.hpp> #include <sprout/config.hpp>
#include <sprout/pit.hpp>
#include <sprout/container/traits.hpp> #include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/algorithm/fixed/result_of.hpp> #include <sprout/algorithm/fixed/result_of.hpp>
@ -37,7 +36,7 @@ namespace sprout {
{} {}
template<typename Result> template<typename Result>
SPROUT_CONSTEXPR operator Result() const { SPROUT_CONSTEXPR operator Result() const {
return sprout::range::fixed::copy(*this, sprout::pit<Result>()); return sprout::range::fixed::copy<Result>(*this);
} }
}; };

View file

@ -7,6 +7,7 @@
#include <sprout/container/traits.hpp> #include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/transform_iterator.hpp> #include <sprout/iterator/transform_iterator.hpp>
#include <sprout/iterator/replace_iterator.hpp>
#include <sprout/range/adaptor/detail/adapted_range_default.hpp> #include <sprout/range/adaptor/detail/adapted_range_default.hpp>
#include <sprout/range/algorithm/copy.hpp> #include <sprout/range/algorithm/copy.hpp>
#include <sprout/type_traits/lvalue_reference.hpp> #include <sprout/type_traits/lvalue_reference.hpp>
@ -15,25 +16,6 @@
namespace sprout { namespace sprout {
namespace adaptors { namespace adaptors {
namespace detail {
template<typename T>
class replace_value {
public:
typedef T const& result_type;
typedef T const& argument_type;
private:
T old_;
T new_;
public:
SPROUT_CONSTEXPR replace_value(T const& old_value, T const& new_value)
: old_(old_value)
, new_(new_value)
{}
SPROUT_CONSTEXPR T operator()(T const& value) const {
return (value == old_) ? new_ : value;
}
};
} // namespace detail
// //
// replaced_range // replaced_range
// //
@ -42,7 +24,7 @@ namespace sprout {
: public sprout::adaptors::detail::adapted_range_default< : public sprout::adaptors::detail::adapted_range_default<
Range, Range,
sprout::transform_iterator< sprout::transform_iterator<
sprout::adaptors::detail::replace_value<typename sprout::container_traits<Range>::value_type>, sprout::replace_value<typename sprout::container_traits<Range>::value_type>,
typename sprout::container_traits<Range>::iterator typename sprout::container_traits<Range>::iterator
> >
> >
@ -51,7 +33,7 @@ namespace sprout {
typedef sprout::adaptors::detail::adapted_range_default< typedef sprout::adaptors::detail::adapted_range_default<
Range, Range,
sprout::transform_iterator< sprout::transform_iterator<
sprout::adaptors::detail::replace_value<typename sprout::container_traits<Range>::value_type>, sprout::replace_value<typename sprout::container_traits<Range>::value_type>,
typename sprout::container_traits<Range>::iterator typename sprout::container_traits<Range>::iterator
> >
> base_type; > base_type;

View file

@ -7,6 +7,7 @@
#include <sprout/container/traits.hpp> #include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
#include <sprout/iterator/transform_iterator.hpp> #include <sprout/iterator/transform_iterator.hpp>
#include <sprout/iterator/replace_if_iterator.hpp>
#include <sprout/range/adaptor/detail/adapted_range_default.hpp> #include <sprout/range/adaptor/detail/adapted_range_default.hpp>
#include <sprout/range/algorithm/copy.hpp> #include <sprout/range/algorithm/copy.hpp>
#include <sprout/type_traits/lvalue_reference.hpp> #include <sprout/type_traits/lvalue_reference.hpp>
@ -15,26 +16,6 @@
namespace sprout { namespace sprout {
namespace adaptors { namespace adaptors {
namespace detail {
template<typename Predicate, typename T>
class replace_value_if {
public:
typedef Predicate predicate_type;
typedef T const& result_type;
typedef T const& argument_type;
private:
Predicate pred_;
T new_;
public:
SPROUT_CONSTEXPR replace_value_if(Predicate pred, T const& new_value)
: pred_(pred)
, new_(new_value)
{}
SPROUT_CONSTEXPR T operator()(T const& value) const {
return pred_(value) ? new_ : value;
}
};
} // namespace detail
// //
// replaced_if_range // replaced_if_range
// //
@ -43,7 +24,7 @@ namespace sprout {
: public sprout::adaptors::detail::adapted_range_default< : public sprout::adaptors::detail::adapted_range_default<
Range, Range,
sprout::transform_iterator< sprout::transform_iterator<
sprout::adaptors::detail::replace_value_if<Predicate, typename sprout::container_traits<Range>::value_type>, sprout::replace_value_if<Predicate, typename sprout::container_traits<Range>::value_type>,
typename sprout::container_traits<Range>::iterator typename sprout::container_traits<Range>::iterator
> >
> >
@ -53,7 +34,7 @@ namespace sprout {
typedef sprout::adaptors::detail::adapted_range_default< typedef sprout::adaptors::detail::adapted_range_default<
Range, Range,
sprout::transform_iterator< sprout::transform_iterator<
sprout::adaptors::detail::replace_value_if<Predicate, typename sprout::container_traits<Range>::value_type>, sprout::replace_value_if<Predicate, typename sprout::container_traits<Range>::value_type>,
typename sprout::container_traits<Range>::iterator typename sprout::container_traits<Range>::iterator
> >
> base_type; > base_type;

View file

@ -18,6 +18,12 @@ namespace sprout {
copy(Input const& input, Result const& result) { copy(Input const& input, Result const& result) {
return sprout::fixed::copy(sprout::begin(input), sprout::end(input), result); return sprout::fixed::copy(sprout::begin(input), sprout::end(input), result);
} }
template<typename Result, typename Input>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy(Input const& input) {
return sprout::fixed::copy<Result>(sprout::begin(input), sprout::end(input));
}
} // namespace fixed } // namespace fixed
using sprout::range::fixed::copy; using sprout::range::fixed::copy;

View file

@ -18,6 +18,12 @@ namespace sprout {
copy_backward(Input const& input, Result const& result) { copy_backward(Input const& input, Result const& result) {
return sprout::fixed::copy_backward(sprout::begin(input), sprout::end(input), result); return sprout::fixed::copy_backward(sprout::begin(input), sprout::end(input), result);
} }
template<typename Result, typename Input>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy_backward(Input const& input) {
return sprout::fixed::copy_backward<Result>(sprout::begin(input), sprout::end(input));
}
} // namespace fixed } // namespace fixed
using sprout::range::fixed::copy_backward; using sprout::range::fixed::copy_backward;

View file

@ -18,6 +18,12 @@ namespace sprout {
copy_if(Input const& input, Result const& result, Predicate pred) { copy_if(Input const& input, Result const& result, Predicate pred) {
return sprout::fixed::copy_if(sprout::begin(input), sprout::end(input), result); return sprout::fixed::copy_if(sprout::begin(input), sprout::end(input), result);
} }
template<typename Result, typename Input, typename Predicate>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
copy_if(Input const& input, Predicate pred) {
return sprout::fixed::copy_if<Result>(sprout::begin(input), sprout::end(input));
}
} // namespace fixed } // namespace fixed
using sprout::range::fixed::copy_if; using sprout::range::fixed::copy_if;

View file

@ -18,6 +18,12 @@ namespace sprout {
replace_copy(Input const& input, Result const& result, T const& old_value, T const& new_value) { replace_copy(Input const& input, Result const& result, T const& old_value, T const& new_value) {
return sprout::fixed::replace_copy(sprout::begin(input), sprout::end(input), result, old_value, new_value); return sprout::fixed::replace_copy(sprout::begin(input), sprout::end(input), result, old_value, new_value);
} }
template<typename Result, typename Input, typename T>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
replace_copy(Input const& input, T const& old_value, T const& new_value) {
return sprout::fixed::replace_copy<Result>(sprout::begin(input), sprout::end(input), old_value, new_value);
}
} // namespace fixed } // namespace fixed
using sprout::range::fixed::replace_copy; using sprout::range::fixed::replace_copy;

View file

@ -18,6 +18,12 @@ namespace sprout {
replace_copy_if(Input const& input, Result const& result, Predicate pred, T const& new_value) { replace_copy_if(Input const& input, Result const& result, Predicate pred, T const& new_value) {
return sprout::fixed::replace_copy_if(sprout::begin(input), sprout::end(input), result, pred, new_value); return sprout::fixed::replace_copy_if(sprout::begin(input), sprout::end(input), result, pred, new_value);
} }
template<typename Result, typename Input, typename T, typename Predicate>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
replace_copy_if(Input const& input, Predicate pred, T const& new_value) {
return sprout::fixed::replace_copy_if<Result>(sprout::begin(input), sprout::end(input), pred, new_value);
}
} // namespace fixed } // namespace fixed
using sprout::range::fixed::replace_copy_if; using sprout::range::fixed::replace_copy_if;

View file

@ -23,6 +23,17 @@ namespace sprout {
transform(Input1 const& input1, Input2 const& input2, Result const& result, BinaryOperation op) { transform(Input1 const& input1, Input2 const& input2, Result const& result, BinaryOperation op) {
return sprout::fixed::transform(sprout::begin(input1), sprout::end(input1), sprout::begin(input2), result, op); return sprout::fixed::transform(sprout::begin(input1), sprout::end(input1), sprout::begin(input2), result, op);
} }
template<typename Result, typename Input, typename UnaryOperation>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
transform(Input const& input, UnaryOperation op) {
return sprout::fixed::transform<Result>(sprout::begin(input), sprout::end(input), op);
}
template<typename Result, typename Input1, typename Input2, typename BinaryOperation>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
transform(Input1 const& input1, Input2 const& input2, BinaryOperation op) {
return sprout::fixed::transform<Result>(sprout::begin(input1), sprout::end(input1), sprout::begin(input2), op);
}
} // namespace fixed } // namespace fixed
using sprout::range::fixed::transform; using sprout::range::fixed::transform;

View file

@ -10,7 +10,6 @@
#include <sprout/container/functions.hpp> #include <sprout/container/functions.hpp>
namespace sprout { namespace sprout {
// //
// container_construct_traits // container_construct_traits
// //
@ -63,7 +62,7 @@ namespace sprout {
return remake_impl( return remake_impl(
sprout::forward<Cont>(cont), sprout::forward<Cont>(cont),
size, size,
sprout::make<internal_type>(sprout::forward<Args>(args)...) sprout::remake<internal_type>(cont, size, sprout::forward<Args>(args)...)
); );
} }
}; };