1
0
Fork 0
mirror of https://github.com/bolero-MURAKAMI/Sprout synced 2025-02-04 21:33:56 +00:00

add algorithm clamp, clamp_range_copy, clamp_range

This commit is contained in:
bolero-MURAKAMI 2012-10-13 21:06:32 +09:00
parent de41f5c880
commit 79ea4f0885
29 changed files with 870 additions and 11 deletions

View file

@ -0,0 +1,143 @@
#ifndef SPROUT_LIBS_ALGORITHM_TEST_CLAMP_RANGE_CPP
#define SPROUT_LIBS_ALGORITHM_TEST_CLAMP_RANGE_CPP
#include <sprout/algorithm/clamp_range.hpp>
#include <sprout/array.hpp>
#include <sprout/sub_array.hpp>
#include <sprout/container.hpp>
#include <testspr/tools.hpp>
namespace testspr {
static void algorithm_clamp_range_test() {
using namespace sprout;
{
SPROUT_STATIC_CONSTEXPR auto arr1 = array<int, 10>{{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}};
// クランプ (4 <= x <= 7)
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range(
arr1,
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 10>{{4, 4, 4, 4, 5, 6, 7, 7, 7, 7}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range(
arr1,
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 10>{{4, 4, 4, 4, 5, 6, 7, 7, 7, 7}}
));
}
// クランプ (4 <= x <= 7)
// 範囲の切り出し
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range(
sprout::sub(arr1, 2, 8),
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
TESTSPR_BOTH_ASSERT(testspr::equal(
sprout::get_internal(clamped),
array<int, 10>{{1, 2, 4, 4, 5, 6, 7, 7, 9, 10}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range(
sprout::sub(arr1, 2, 8),
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
TESTSPR_BOTH_ASSERT(testspr::equal(
sprout::get_internal(clamped),
array<int, 10>{{1, 2, 4, 4, 5, 6, 7, 7, 9, 10}}
));
}
}
{
SPROUT_STATIC_CONSTEXPR auto arr1 = array<int, 10>{{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}};
// クランプ (4 <= x <= 7)
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range(
arr1,
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 10>{{4, 4, 4, 4, 5, 6, 7, 7, 7, 7}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range(
arr1,
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 10>{{4, 4, 4, 4, 5, 6, 7, 7, 7, 7}}
));
}
// クランプ (4 <= x <= 7)
// 範囲の切り出し
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range(
sprout::sub(arr1, 2, 8),
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
TESTSPR_BOTH_ASSERT(testspr::equal(
sprout::get_internal(clamped),
array<int, 10>{{1, 2, 4, 4, 5, 6, 7, 7, 9, 10}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range(
sprout::sub(arr1, 2, 8),
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
TESTSPR_BOTH_ASSERT(testspr::equal(
sprout::get_internal(clamped),
array<int, 10>{{1, 2, 4, 4, 5, 6, 7, 7, 9, 10}}
));
}
}
}
} // namespace testspr
#ifndef TESTSPR_CPP_INCLUDE
# define TESTSPR_TEST_FUNCTION testspr::algorithm_clamp_range_test
# include <testspr/include_main.hpp>
#endif
#endif // #ifndef SPROUT_LIBS_ALGORITHM_TEST_CLAMP_RANGE_CPP

View file

@ -0,0 +1,221 @@
#ifndef SPROUT_LIBS_ALGORITHM_TEST_CLAMP_RANGE_COPY_CPP
#define SPROUT_LIBS_ALGORITHM_TEST_CLAMP_RANGE_COPY_CPP
#include <sprout/algorithm/clamp_range_copy.hpp>
#include <sprout/array.hpp>
#include <sprout/sub_array.hpp>
#include <sprout/container.hpp>
#include <testspr/tools.hpp>
namespace testspr {
static void algorithm_clamp_range_copy_test() {
using namespace sprout;
{
SPROUT_STATIC_CONSTEXPR auto arr1 = array<int, 10>{{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}};
SPROUT_STATIC_CONSTEXPR auto arr2 = array<int, 10>{};
SPROUT_STATIC_CONSTEXPR auto arr3 = array<int, 4>{};
// [2 .. 8) の範囲をクランプ (4 <= x <= 7)
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
arr2,
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 10>{{4, 4, 5, 6, 7, 7, 0, 0, 0, 0}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
arr2,
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
}
// [2 .. 8) の範囲をクランプ (4 <= x <= 7)
// 出力範囲をオーバーする場合
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
arr3,
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 4>{{4, 4, 5, 6}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
arr3,
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 4>{{4, 4, 5, 6}}
));
}
// [2 .. 8) の範囲をクランプ (4 <= x <= 7)
// 出力範囲の切り出し
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
sprout::sub(arr2, 2, 8),
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
TESTSPR_BOTH_ASSERT(testspr::equal(
sprout::get_internal(clamped),
array<int, 10>{{0, 0, 4, 4, 5, 6, 7, 7, 0, 0}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
sprout::sub(arr2, 2, 8),
4,
7
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
TESTSPR_BOTH_ASSERT(testspr::equal(
sprout::get_internal(clamped),
array<int, 10>{{0, 0, 4, 4, 5, 6, 7, 7, 0, 0}}
));
}
}
{
SPROUT_STATIC_CONSTEXPR auto arr1 = array<int, 10>{{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}};
SPROUT_STATIC_CONSTEXPR auto arr2 = array<int, 10>{};
SPROUT_STATIC_CONSTEXPR auto arr3 = array<int, 4>{};
// [2 .. 8) の範囲をクランプ (4 <= x <= 7)
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
arr2,
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 10>{{4, 4, 5, 6, 7, 7, 0, 0, 0, 0}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
arr2,
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
}
// [2 .. 8) の範囲をクランプ (4 <= x <= 7)
// 出力範囲をオーバーする場合
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
arr3,
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 4>{{4, 4, 5, 6}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
arr3,
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 4>{{4, 4, 5, 6}}
));
}
// [2 .. 8) の範囲をクランプ (4 <= x <= 7)
// 出力範囲の切り出し
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
sprout::sub(arr2, 2, 8),
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
TESTSPR_BOTH_ASSERT(testspr::equal(
sprout::get_internal(clamped),
array<int, 10>{{0, 0, 4, 4, 5, 6, 7, 7, 0, 0}}
));
}
{
SPROUT_STATIC_CONSTEXPR auto clamped = sprout::fit::clamp_range_copy(
sprout::begin(arr1) + 2,
sprout::begin(arr1) + 8,
sprout::sub(arr2, 2, 8),
4,
7,
testspr::less<int>()
);
TESTSPR_BOTH_ASSERT(testspr::equal(
clamped,
array<int, 6>{{4, 4, 5, 6, 7, 7}}
));
TESTSPR_BOTH_ASSERT(testspr::equal(
sprout::get_internal(clamped),
array<int, 10>{{0, 0, 4, 4, 5, 6, 7, 7, 0, 0}}
));
}
}
}
} // namespace testspr
#ifndef TESTSPR_CPP_INCLUDE
# define TESTSPR_TEST_FUNCTION testspr::algorithm_clamp_range_copy_test
# include <testspr/include_main.hpp>
#endif
#endif // #ifndef SPROUT_LIBS_ALGORITHM_TEST_CLAMP_RANGE_COPY_CPP

View file

@ -56,6 +56,8 @@
#include "./sort_heap.cpp"
#include "./next_permutation.cpp"
#include "./prev_permutation.cpp"
#include "./clamp_range_copy.cpp"
#include "./clamp_range.cpp"
#include "./swap_element.cpp"
#include "./swap_element_copy.cpp"
#include "./random_swap.cpp"
@ -121,6 +123,8 @@ namespace testspr {
testspr::algorithm_sort_heap_test();
testspr::algorithm_next_permutation_test();
testspr::algorithm_prev_permutation_test();
testspr::algorithm_clamp_range_copy_test();
testspr::algorithm_clamp_range_test();
testspr::algorithm_swap_element_test();
testspr::algorithm_swap_element_copy_test();
testspr::algorithm_random_swap_test();

View file

@ -14,7 +14,7 @@ namespace sprout {
inline SPROUT_CONSTEXPR ForwardIterator
adjacent_find(ForwardIterator first, ForwardIterator last, BinaryPredicate pred) {
return first == last || sprout::next(first) == last ? last
: pred(*first, *(sprout::next(first))) != false ? first
: pred(*first, *(sprout::next(first))) ? first
: sprout::adjacent_find(sprout::next(first), last, pred)
;
}

View file

@ -12,7 +12,7 @@ namespace sprout {
inline SPROUT_CONSTEXPR bool
all_of(InputIterator first, InputIterator last, Predicate pred) {
return first == last ? true
: pred(*first) == true && sprout::all_of(sprout::next(first), last, pred)
: pred(*first) && sprout::all_of(sprout::next(first), last, pred)
;
}
} // namespace sprout

View file

@ -12,7 +12,7 @@ namespace sprout {
inline SPROUT_CONSTEXPR bool
any_of(InputIterator first, InputIterator last, Predicate pred) {
return first == last ? false
: pred(*first) == true || sprout::any_of(sprout::next(first), last, pred)
: pred(*first) || sprout::any_of(sprout::next(first), last, pred)
;
}
} // namespace sprout

View file

@ -0,0 +1,30 @@
#ifndef SPROUT_ALGORITHM_CLAMP_HPP
#define SPROUT_ALGORITHM_CLAMP_HPP
#include <type_traits>
#include <sprout/config.hpp>
#include HDR_FUNCTIONAL_SSCRISK_CEL_OR_SPROUT
namespace sprout {
//
// clamp
//
template<typename T, typename Compare>
inline SPROUT_CONSTEXPR T const&
clamp(T const& value, typename std::common_type<T>::type const& low, typename std::common_type<T>::type const& high, Compare comp) {
return comp(value, low) ? low
: comp(high, value) ? high
: value
;
}
template<typename T>
inline SPROUT_CONSTEXPR T const&
clamp(T const& value, typename std::common_type<T>::type const& low, typename std::common_type<T>::type const& high) {
return sprout::clamp(
value, low, high,
NS_SSCRISK_CEL_OR_SPROUT::less<T>()
);
}
} // namespace sprout
#endif // #ifndef SPROUT_ALGORITHM_CLAMP_HPP

View file

@ -0,0 +1,8 @@
#ifndef SPROUT_ALGORITHM_CLAMP_RANGE_HPP
#define SPROUT_ALGORITHM_CLAMP_RANGE_HPP
#include <sprout/config.hpp>
#include <sprout/algorithm/fixed/clamp_range.hpp>
#include <sprout/algorithm/fit/clamp_range.hpp>
#endif // #ifndef SPROUT_ALGORITHM_CLAMP_RANGE_HPP

View file

@ -0,0 +1,8 @@
#ifndef SPROUT_ALGORITHM_CLAMP_RANGE_COPY_HPP
#define SPROUT_ALGORITHM_CLAMP_RANGE_COPY_HPP
#include <sprout/config.hpp>
#include <sprout/algorithm/fixed/clamp_range_copy.hpp>
#include <sprout/algorithm/fit/clamp_range_copy.hpp>
#endif // #ifndef SPROUT_ALGORITHM_CLAMP_RANGE_COPY_HPP

View file

@ -13,7 +13,7 @@ namespace sprout {
inline SPROUT_CONSTEXPR typename std::iterator_traits<InputIterator>::difference_type
count_if(InputIterator first, InputIterator last, Predicate pred) {
return first == last ? 0
: (pred(*first) != false ? 1 : 0) + sprout::count_if(sprout::next(first), last, pred)
: (pred(*first) ? 1 : 0) + sprout::count_if(sprout::next(first), last, pred)
;
}
} // namespace sprout

View file

@ -20,7 +20,7 @@ namespace sprout {
inline SPROUT_CONSTEXPR bool
equal(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, BinaryPredicate pred) {
return first1 == last1 ? true
: pred(*first1, *first2) != false && sprout::equal(sprout::next(first1), last1, sprout::next(first2), pred)
: pred(*first1, *first2) && sprout::equal(sprout::next(first1), last1, sprout::next(first2), pred)
;
}
} // namespace sprout

View file

@ -11,7 +11,7 @@ namespace sprout {
template<typename InputIterator, typename Predicate>
inline SPROUT_CONSTEXPR InputIterator
find_if(InputIterator first, InputIterator last, Predicate pred) {
return first == last || pred(*first) != false ? first
return first == last || pred(*first) ? first
: sprout::find_if(sprout::next(first), last, pred)
;
}

View file

@ -11,7 +11,7 @@ namespace sprout {
template<typename InputIterator, typename Predicate>
inline SPROUT_CONSTEXPR InputIterator
find_if_not(InputIterator first, InputIterator last, Predicate pred) {
return first == last || pred(*first) == false ? first
return first == last || !pred(*first) ? first
: sprout::find_if_not(sprout::next(first), last, pred)
;
}

View file

@ -52,6 +52,8 @@
#include <sprout/algorithm/fit/sort_heap.hpp>
#include <sprout/algorithm/fit/next_permutation.hpp>
#include <sprout/algorithm/fit/prev_permutation.hpp>
#include <sprout/algorithm/fit/clamp_range_copy.hpp>
#include <sprout/algorithm/fit/clamp_range.hpp>
#include <sprout/algorithm/fit/random_swap.hpp>
#include <sprout/algorithm/fit/random_swap_result.hpp>
#include <sprout/algorithm/fit/bogo_sort.hpp>

View file

@ -0,0 +1,79 @@
#ifndef SPROUT_ALGORITHM_FIT_CLAMP_RANGE_HPP
#define SPROUT_ALGORITHM_FIT_CLAMP_RANGE_HPP
#include <sprout/config.hpp>
#include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp>
#include <sprout/algorithm/fixed/clamp_range.hpp>
#include <sprout/algorithm/fit/result_of.hpp>
#include <sprout/sub_array.hpp>
namespace sprout {
namespace fit {
namespace detail {
template<typename Container, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Container>::type
clamp_range_impl(
Container const& cont,
typename sprout::container_traits<Container>::value_type const& low,
typename sprout::container_traits<Container>::value_type const& high,
Compare comp,
typename sprout::container_traits<Container>::difference_type offset
)
{
return sprout::sub_copy(
sprout::get_internal(sprout::fixed::clamp_range(cont, low, high, comp)),
offset,
offset + sprout::size(cont)
);
}
} // namespace detail
//
// clamp_range
//
template<typename Container, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Container>::type
clamp_range(
Container const& cont,
typename sprout::container_traits<Container>::value_type const& low,
typename sprout::container_traits<Container>::value_type const& high,
Compare comp
)
{
return sprout::fit::detail::clamp_range_impl(cont, low, high, comp, sprout::internal_begin_offset(cont));
}
namespace detail {
template<typename Container>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Container>::type
clamp_range_impl(
Container const& cont,
typename sprout::container_traits<Container>::value_type const& low,
typename sprout::container_traits<Container>::value_type const& high,
typename sprout::container_traits<Container>::difference_type offset
)
{
return sprout::sub_copy(
sprout::get_internal(sprout::fixed::clamp_range(cont, low, high)),
offset,
offset + sprout::size(cont)
);
}
} // namespace detail
//
// clamp_range
//
template<typename Container>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Container>::type
clamp_range(
Container const& cont,
typename sprout::container_traits<Container>::value_type const& low,
typename sprout::container_traits<Container>::value_type const& high
)
{
return sprout::fit::detail::clamp_range_impl(cont, low, high, sprout::internal_begin_offset(cont));
}
} // namespace fit
} // namespace sprout
#endif // #ifndef SPROUT_ALGORITHM_FIT_CLAMP_RANGE_HPP

View file

@ -0,0 +1,81 @@
#ifndef SPROUT_ALGORITHM_FIT_CLAMP_RANGE_COPY_HPP
#define SPROUT_ALGORITHM_FIT_CLAMP_RANGE_COPY_HPP
#include <sprout/config.hpp>
#include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp>
#include <sprout/algorithm/fixed/clamp_range_copy.hpp>
#include <sprout/algorithm/fit/result_of.hpp>
#include <sprout/sub_array.hpp>
#include HDR_ALGORITHM_SSCRISK_CEL_OR_SPROUT
#include HDR_ITERATOR_SSCRISK_CEL_OR_SPROUT
namespace sprout {
namespace fit {
namespace detail {
template<typename InputIterator, typename Result, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Result>::type
clamp_range_copy_impl(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high,
Compare comp,
typename sprout::container_traits<Result>::difference_type offset
)
{
return sprout::sub_copy(
sprout::get_internal(sprout::fixed::clamp_range_copy(first, last, result, low, high, comp)),
offset,
offset + NS_SSCRISK_CEL_OR_SPROUT::min(NS_SSCRISK_CEL_OR_SPROUT::distance(first, last), sprout::size(result))
);
}
} // namespace detail
//
// clamp_range_copy
//
template<typename InputIterator, typename Result, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Result>::type
clamp_range_copy(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high,
Compare comp
)
{
return sprout::fit::detail::clamp_range_copy_impl(first, last, result, low, high, comp, sprout::internal_begin_offset(result));
}
namespace detail {
template<typename InputIterator, typename Result>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Result>::type
clamp_range_copy_impl(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high,
typename sprout::container_traits<Result>::difference_type offset
)
{
return sprout::sub_copy(
sprout::get_internal(sprout::fixed::clamp_range_copy(first, last, result, low, high)),
offset,
offset + NS_SSCRISK_CEL_OR_SPROUT::min(NS_SSCRISK_CEL_OR_SPROUT::distance(first, last), sprout::size(result))
);
}
} // namespace detail
//
// clamp_range_copy
//
template<typename InputIterator, typename Result>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Result>::type
clamp_range_copy(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high
)
{
return sprout::fit::detail::clamp_range_copy_impl(first, last, result, low, high, sprout::internal_begin_offset(result));
}
} // namespace fit
} // namespace sprout
#endif // #ifndef SPROUT_ALGORITHM_FIT_CLAMP_RANGE_COPY_HPP

View file

@ -52,6 +52,8 @@
#include <sprout/algorithm/fixed/sort_heap.hpp>
#include <sprout/algorithm/fixed/next_permutation.hpp>
#include <sprout/algorithm/fixed/prev_permutation.hpp>
#include <sprout/algorithm/fixed/clamp_range_copy.hpp>
#include <sprout/algorithm/fixed/clamp_range.hpp>
#include <sprout/algorithm/fixed/swap_element.hpp>
#include <sprout/algorithm/fixed/swap_element_copy.hpp>
#include <sprout/algorithm/fixed/random_swap.hpp>

View file

@ -0,0 +1,41 @@
#ifndef SPROUT_ALGORITHM_FIXED_CLAMP_RANGE_HPP
#define SPROUT_ALGORITHM_FIXED_CLAMP_RANGE_HPP
#include <sprout/config.hpp>
#include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp>
#include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/algorithm/fixed/clamp_range_copy.hpp>
namespace sprout {
namespace fixed {
//
// clamp_range
//
template<typename Container, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Container>::type
clamp_range(
Container const& cont,
typename sprout::container_traits<Container>::value_type const& low,
typename sprout::container_traits<Container>::value_type const& high,
Compare comp
)
{
return sprout::fixed::clamp_range_copy(sprout::begin(cont), sprout::end(cont), cont, low, high, comp);
}
template<typename Container>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Container>::type
clamp_range(
Container const& cont,
typename sprout::container_traits<Container>::value_type const& low,
typename sprout::container_traits<Container>::value_type const& high
)
{
return sprout::fixed::clamp_range_copy(sprout::begin(cont), sprout::end(cont), cont, low, high);
}
} // namespace fixed
using sprout::fixed::clamp_range;
} // namespace sprout
#endif // #ifndef SPROUT_ALGORITHM_FIXED_CLAMP_RANGE_HPP

View file

@ -0,0 +1,145 @@
#ifndef SPROUT_ALGORITHM_FIXED_CLAMP_RANGE_COPY_HPP
#define SPROUT_ALGORITHM_FIXED_CLAMP_RANGE_COPY_HPP
#include <iterator>
#include <type_traits>
#include <sprout/config.hpp>
#include <sprout/index_tuple.hpp>
#include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp>
#include <sprout/iterator/operation.hpp>
#include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/algorithm/clamp.hpp>
#include <sprout/detail/container_complate.hpp>
#include HDR_ITERATOR_SSCRISK_CEL_OR_SPROUT
#include HDR_FUNCTIONAL_SSCRISK_CEL_OR_SPROUT
namespace sprout {
namespace fixed {
namespace detail {
template<typename RandomAccessIterator, typename Result, typename Compare, sprout::index_t... Indexes>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
clamp_range_copy_impl_ra(
RandomAccessIterator first, RandomAccessIterator last, Result const& result,
typename std::iterator_traits<RandomAccessIterator>::value_type const& low,
typename std::iterator_traits<RandomAccessIterator>::value_type const& high,
Compare comp,
sprout::index_tuple<Indexes...>,
typename sprout::container_traits<Result>::difference_type offset,
typename sprout::container_traits<Result>::size_type size,
typename sprout::container_traits<Result>::size_type input_size
)
{
return sprout::remake<Result>(
result,
sprout::size(result),
(Indexes >= offset && Indexes < offset + size && Indexes < offset + input_size
? sprout::clamp(first[Indexes - offset], low, high, comp)
: *sprout::next(sprout::internal_begin(result), Indexes)
)...
);
}
template<typename RandomAccessIterator, typename Result, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
clamp_range_copy(
RandomAccessIterator first, RandomAccessIterator last, Result const& result,
typename std::iterator_traits<RandomAccessIterator>::value_type const& low,
typename std::iterator_traits<RandomAccessIterator>::value_type const& high,
Compare comp,
std::random_access_iterator_tag*
)
{
return sprout::fixed::detail::clamp_range_copy_impl_ra(
first, last, result, low, high, comp,
sprout::index_range<0, sprout::container_traits<Result>::static_size>::make(),
sprout::internal_begin_offset(result),
sprout::size(result),
NS_SSCRISK_CEL_OR_SPROUT::distance(first, last)
);
}
template<typename InputIterator, typename Result, typename Compare, typename... Args>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::container_traits<Result>::static_size == sizeof...(Args),
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
clamp_range_copy_impl(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high,
Compare comp,
typename sprout::container_traits<Result>::size_type size,
Args const&... args
)
{
return sprout::remake<Result>(result, sprout::size(result), args...);
}
template<typename InputIterator, typename Result, typename Compare, typename... Args>
inline SPROUT_CONSTEXPR typename std::enable_if<
sprout::container_traits<Result>::static_size != sizeof...(Args),
typename sprout::fixed::result_of::algorithm<Result>::type
>::type
clamp_range_copy_impl(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high,
Compare comp,
typename sprout::container_traits<Result>::size_type size,
Args const&... args
)
{
return first != last && sizeof...(Args) < size
? clamp_range_copy_impl(
sprout::next(first), last, result, low, high, comp,
size,
args..., sprout::clamp(*first, low, high, comp)
)
: sprout::detail::container_complate(result, args...)
;
}
template<typename InputIterator, typename Result, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
clamp_range_copy(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high,
Compare comp,
void*
)
{
return sprout::fixed::detail::clamp_range_copy_impl(first, last, result, low, high, comp, sprout::size(result));
}
} // namespace detail
//
// clamp_range_copy
//
template<typename InputIterator, typename Result, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
clamp_range_copy(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high,
Compare comp
)
{
typedef typename std::iterator_traits<InputIterator>::iterator_category* category;
return sprout::fixed::detail::clamp_range_copy(first, last, result, low, high, comp, category());
}
template<typename InputIterator, typename Result>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
clamp_range_copy(
InputIterator first, InputIterator last, Result const& result,
typename std::iterator_traits<InputIterator>::value_type const& low,
typename std::iterator_traits<InputIterator>::value_type const& high
)
{
return sprout::fixed::clamp_range_copy(
first, last, result, low, high,
NS_SSCRISK_CEL_OR_SPROUT::less<typename std::iterator_traits<InputIterator>::value_type>()
);
}
} // namespace fixed
using sprout::fixed::clamp_range_copy;
} // namespace sprout
#endif // #ifndef SPROUT_ALGORITHM_FIXED_CLAMP_RANGE_COPY_HPP

View file

@ -21,7 +21,7 @@ namespace sprout {
inline SPROUT_CONSTEXPR ForwardIterator
is_sorted_until(ForwardIterator first, ForwardIterator last, Compare comp) {
return first == last || sprout::next(first) == last ? last
: comp(*(sprout::next(first)), *first) != false ? sprout::next(first)
: comp(*(sprout::next(first)), *first) ? sprout::next(first)
: sprout::is_sorted_until(sprout::next(first), last)
;
}

View file

@ -21,7 +21,7 @@ namespace sprout {
template<typename InputIterator1, typename InputIterator2, typename BinaryPredicate>
inline SPROUT_CONSTEXPR sprout::pair<InputIterator1, InputIterator2>
mismatch(InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, BinaryPredicate pred) {
return first1 == last1 || pred(*first1, *first2) == false
return first1 == last1 || !pred(*first1, *first2)
? sprout::pair<InputIterator1, InputIterator2>{first1, first2}
: sprout::mismatch(sprout::next(first1), last1, sprout::next(first2))
;

View file

@ -45,5 +45,6 @@
#include <sprout/algorithm/is_decreasing.hpp>
#include <sprout/algorithm/is_strictly_increasing.hpp>
#include <sprout/algorithm/is_strictly_decreasing.hpp>
#include <sprout/algorithm/clamp.hpp>
#endif // #ifndef SPROUT_ALGORITHM_NON_MODIFYIING_HPP

View file

@ -12,7 +12,7 @@ namespace sprout {
inline SPROUT_CONSTEXPR bool
none_of(InputIterator first, InputIterator last, Predicate pred) {
return first == last ? true
: pred(*first) == false && sprout::none_of(sprout::next(first), last, pred)
: !pred(*first) && sprout::none_of(sprout::next(first), last, pred)
;
}
} // namespace sprout

View file

@ -47,7 +47,7 @@ namespace sprout {
return sprout::find_if(first, last, pred);
}
static SPROUT_CONSTEXPR iterator_type find_prev(iterator_type first, predicate_type pred) {
return pred(*first) != false ? first
return pred(*first) ? first
: find_prev(sprout::prev(first), pred)
;
}

View file

@ -0,0 +1,8 @@
#ifndef SPROUT_RANGE_ALGORITHM_CLAMP_RANGE_COPY_HPP
#define SPROUT_RANGE_ALGORITHM_CLAMP_RANGE_COPY_HPP
#include <sprout/config.hpp>
#include <sprout/range/algorithm/fixed/clamp_range_copy.hpp>
#include <sprout/range/algorithm/fit/clamp_range_copy.hpp>
#endif // #ifndef SPROUT_RANGE_ALGORITHM_CLAMP_RANGE_COPY_HPP

View file

@ -20,6 +20,7 @@
#include <sprout/range/algorithm/fit/set_intersection.hpp>
#include <sprout/range/algorithm/fit/set_difference.hpp>
#include <sprout/range/algorithm/fit/set_symmetric_difference.hpp>
#include <sprout/range/algorithm/fit/clamp_range_copy.hpp>
#include <sprout/range/algorithm/fit/swap_element_copy.hpp>
#endif // #ifndef SPROUT_RANGE_ALGORITHM_FIT_HPP

View file

@ -0,0 +1,41 @@
#ifndef SPROUT_RANGE_ALGORITHM_FIT_CLAMP_RANGE_COPY_HPP
#define SPROUT_RANGE_ALGORITHM_FIT_CLAMP_RANGE_COPY_HPP
#include <sprout/config.hpp>
#include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp>
#include <sprout/algorithm/fit/result_of.hpp>
#include <sprout/algorithm/fit/clamp_range_copy.hpp>
namespace sprout {
namespace range {
namespace fit {
//
// clamp_range_copy
//
template<typename Input, typename Result, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Result>::type
clamp_range_copy(
Input const& input, Result const& result,
typename sprout::container_traits<Input>::value_type const& low,
typename sprout::container_traits<Input>::value_type const& high,
Compare comp
)
{
return sprout::fit::clamp_range_copy(sprout::begin(input), sprout::end(input), result, low, high, comp);
}
template<typename Input, typename Result>
inline SPROUT_CONSTEXPR typename sprout::fit::result_of::algorithm<Result>::type
clamp_range_copy(
Input const& input, Result const& result,
typename sprout::container_traits<Input>::value_type const& low,
typename sprout::container_traits<Input>::value_type const& high
)
{
return sprout::fit::clamp_range_copy(sprout::begin(input), sprout::end(input), result, low, high);
}
} // namespace fit
} // namespace range
} // namespace sprout
#endif // #ifndef SPROUT_RANGE_ALGORITHM_FIT_CLAMP_RANGE_COPY_HPP

View file

@ -20,6 +20,7 @@
#include <sprout/range/algorithm/fixed/set_intersection.hpp>
#include <sprout/range/algorithm/fixed/set_difference.hpp>
#include <sprout/range/algorithm/fixed/set_symmetric_difference.hpp>
#include <sprout/range/algorithm/fixed/clamp_range_copy.hpp>
#include <sprout/range/algorithm/fixed/swap_element_copy.hpp>
#endif // #ifndef SPROUT_RANGE_ALGORITHM_FIXED_HPP

View file

@ -0,0 +1,43 @@
#ifndef SPROUT_RANGE_ALGORITHM_FIXED_CLAMP_RANGE_COPY_HPP
#define SPROUT_RANGE_ALGORITHM_FIXED_CLAMP_RANGE_COPY_HPP
#include <sprout/config.hpp>
#include <sprout/container/traits.hpp>
#include <sprout/container/functions.hpp>
#include <sprout/algorithm/fixed/result_of.hpp>
#include <sprout/algorithm/fixed/clamp_range_copy.hpp>
namespace sprout {
namespace range {
namespace fixed {
//
// clamp_range_copy
//
template<typename Input, typename Result, typename Compare>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
clamp_range_copy(
Input const& input, Result const& result,
typename sprout::container_traits<Input>::value_type const& low,
typename sprout::container_traits<Input>::value_type const& high,
Compare comp
)
{
return sprout::fixed::clamp_range_copy(sprout::begin(input), sprout::end(input), result, low, high, comp);
}
template<typename Input, typename Result>
inline SPROUT_CONSTEXPR typename sprout::fixed::result_of::algorithm<Result>::type
clamp_range_copy(
Input const& input, Result const& result,
typename sprout::container_traits<Input>::value_type const& low,
typename sprout::container_traits<Input>::value_type const& high
)
{
return sprout::fixed::clamp_range_copy(sprout::begin(input), sprout::end(input), result, low, high);
}
} // namespace fixed
using sprout::range::fixed::clamp_range_copy;
} // namespace range
} // namespace sprout
#endif // #ifndef SPROUT_RANGE_ALGORITHM_FIXED_CLAMP_RANGE_COPY_HPP