libstdc++: Synchronize PSTL with upstream
This patch rebases the C++17 parallel algorithms implementation (pstl) against the current upstream version, commit 843c12d6a. This version does not currently include the recently added OpenMP backend, that will be considered for a future version. libstdc++-v3/ChangeLog: * include/pstl/algorithm_fwd.h: Synchronize with upstream. * include/pstl/algorithm_impl.h: Likewise. * include/pstl/execution_defs.h: Likewise. * include/pstl/execution_impl.h: Likewise. * include/pstl/glue_algorithm_impl.h: Likewise. * include/pstl/glue_execution_defs.h: Likewise. * include/pstl/glue_memory_impl.h: Likewise. * include/pstl/glue_numeric_impl.h: Likewise. * include/pstl/memory_impl.h: Likewise. * include/pstl/numeric_fwd.h: Likewise. * include/pstl/numeric_impl.h: Likewise. * include/pstl/parallel_backend.h: Likewise. * include/pstl/parallel_backend_serial.h: Likewise. * include/pstl/parallel_backend_tbb.h: Likewise. * include/pstl/parallel_impl.h: Likewise. * include/pstl/pstl_config.h: Likewise. * include/pstl/unseq_backend_simd.h: Likewise. * include/pstl/utils.h: Likewise. * testsuite/20_util/specialized_algorithms/pstl/uninitialized_construct.cc: Likewise. * testsuite/20_util/specialized_algorithms/pstl/uninitialized_copy_move.cc: Likewise. * testsuite/20_util/specialized_algorithms/pstl/uninitialized_fill_destroy.cc: Likewise. * testsuite/25_algorithms/pstl/alg_merge/inplace_merge.cc: Likewise. * testsuite/25_algorithms/pstl/alg_merge/merge.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/copy_if.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/copy_move.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/fill.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/generate.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/is_partitioned.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/partition.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/partition_copy.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/remove.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/remove_copy.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/replace.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/replace_copy.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/rotate.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/rotate_copy.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/swap_ranges.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/transform_binary.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/transform_unary.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/unique.cc: Likewise. * testsuite/25_algorithms/pstl/alg_modifying_operations/unique_copy_equal.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/adjacent_find.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/all_of.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/any_of.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/count.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/equal.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/find.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/find_end.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/find_first_of.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/find_if.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/for_each.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/mismatch.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/none_of.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/nth_element.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/reverse.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/reverse_copy.cc: Likewise. * testsuite/25_algorithms/pstl/alg_nonmodifying/search_n.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/includes.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/is_heap.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/is_sorted.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/lexicographical_compare.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/minmax_element.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/partial_sort.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/partial_sort_copy.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/set.cc: Likewise. * testsuite/25_algorithms/pstl/alg_sorting/sort.cc: Likewise. * testsuite/26_numerics/pstl/numeric_ops/adjacent_difference.cc: Likewise. * testsuite/26_numerics/pstl/numeric_ops/reduce.cc: Likewise. * testsuite/26_numerics/pstl/numeric_ops/scan.cc: Likewise. * testsuite/26_numerics/pstl/numeric_ops/transform_reduce.cc: Likewise. * testsuite/26_numerics/pstl/numeric_ops/transform_scan.cc: Likewise. * testsuite/util/pstl/test_utils.h: Likewise.
This commit is contained in:
parent
3a39a31b8a
commit
3162ca09db
72 changed files with 3367 additions and 3319 deletions
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
@ -22,88 +22,20 @@ inline namespace v1
|
|||
// 2.4, Sequential execution policy
|
||||
class sequenced_policy
|
||||
{
|
||||
public:
|
||||
// For internal use only
|
||||
static constexpr std::false_type
|
||||
__allow_unsequenced()
|
||||
{
|
||||
return std::false_type{};
|
||||
}
|
||||
static constexpr std::false_type
|
||||
__allow_vector()
|
||||
{
|
||||
return std::false_type{};
|
||||
}
|
||||
static constexpr std::false_type
|
||||
__allow_parallel()
|
||||
{
|
||||
return std::false_type{};
|
||||
}
|
||||
};
|
||||
|
||||
// 2.5, Parallel execution policy
|
||||
class parallel_policy
|
||||
{
|
||||
public:
|
||||
// For internal use only
|
||||
static constexpr std::false_type
|
||||
__allow_unsequenced()
|
||||
{
|
||||
return std::false_type{};
|
||||
}
|
||||
static constexpr std::false_type
|
||||
__allow_vector()
|
||||
{
|
||||
return std::false_type{};
|
||||
}
|
||||
static constexpr std::true_type
|
||||
__allow_parallel()
|
||||
{
|
||||
return std::true_type{};
|
||||
}
|
||||
};
|
||||
|
||||
// 2.6, Parallel+Vector execution policy
|
||||
class parallel_unsequenced_policy
|
||||
{
|
||||
public:
|
||||
// For internal use only
|
||||
static constexpr std::true_type
|
||||
__allow_unsequenced()
|
||||
{
|
||||
return std::true_type{};
|
||||
}
|
||||
static constexpr std::true_type
|
||||
__allow_vector()
|
||||
{
|
||||
return std::true_type{};
|
||||
}
|
||||
static constexpr std::true_type
|
||||
__allow_parallel()
|
||||
{
|
||||
return std::true_type{};
|
||||
}
|
||||
};
|
||||
|
||||
class unsequenced_policy
|
||||
{
|
||||
public:
|
||||
// For internal use only
|
||||
static constexpr std::true_type
|
||||
__allow_unsequenced()
|
||||
{
|
||||
return std::true_type{};
|
||||
}
|
||||
static constexpr std::true_type
|
||||
__allow_vector()
|
||||
{
|
||||
return std::true_type{};
|
||||
}
|
||||
static constexpr std::false_type
|
||||
__allow_parallel()
|
||||
{
|
||||
return std::false_type{};
|
||||
}
|
||||
};
|
||||
|
||||
// 2.8, Execution policy objects
|
||||
|
@ -135,7 +67,7 @@ struct is_execution_policy<__pstl::execution::unsequenced_policy> : std::true_ty
|
|||
{
|
||||
};
|
||||
|
||||
#if _PSTL_CPP14_VARIABLE_TEMPLATES_PRESENT
|
||||
#if defined (_PSTL_CPP14_VARIABLE_TEMPLATES_PRESENT)
|
||||
template <class _Tp>
|
||||
constexpr bool is_execution_policy_v = __pstl::execution::is_execution_policy<_Tp>::value;
|
||||
#endif
|
||||
|
@ -155,6 +87,12 @@ using __enable_if_execution_policy =
|
|||
typename std::enable_if<__pstl::execution::is_execution_policy<typename std::decay<_ExecPolicy>::type>::value,
|
||||
_Tp>::type;
|
||||
#endif
|
||||
|
||||
template <class _IsVector>
|
||||
struct __serial_tag;
|
||||
template <class _IsVector>
|
||||
struct __parallel_tag;
|
||||
|
||||
} // namespace __internal
|
||||
|
||||
} // namespace __pstl
|
||||
|
|
|
@ -20,141 +20,80 @@ namespace __pstl
|
|||
namespace __internal
|
||||
{
|
||||
|
||||
using namespace __pstl::execution;
|
||||
template <typename _IteratorTag, typename... _IteratorTypes>
|
||||
using __are_iterators_of = std::conjunction<
|
||||
std::is_base_of<_IteratorTag, typename std::iterator_traits<std::decay_t<_IteratorTypes>>::iterator_category>...>;
|
||||
|
||||
/* predicate */
|
||||
template <typename... _IteratorTypes>
|
||||
using __are_random_access_iterators = __are_iterators_of<std::random_access_iterator_tag, _IteratorTypes...>;
|
||||
|
||||
template <typename _Tp>
|
||||
std::false_type __lazy_and(_Tp, std::false_type)
|
||||
struct __serial_backend_tag
|
||||
{
|
||||
return std::false_type{};
|
||||
};
|
||||
struct __tbb_backend_tag
|
||||
{
|
||||
};
|
||||
struct __openmp_backend_tag
|
||||
{
|
||||
};
|
||||
|
||||
#if defined(_PSTL_PAR_BACKEND_TBB)
|
||||
using __par_backend_tag = __tbb_backend_tag;
|
||||
#elif defined(_PSTL_PAR_BACKEND_OPENMP)
|
||||
using __par_backend_tag = __openmp_backend_tag;
|
||||
#elif defined(_PSTL_PAR_BACKEND_SERIAL)
|
||||
using __par_backend_tag = __serial_backend_tag;
|
||||
#else
|
||||
# error "A parallel backend must be specified";
|
||||
#endif
|
||||
|
||||
template <class _IsVector>
|
||||
struct __serial_tag
|
||||
{
|
||||
using __is_vector = _IsVector;
|
||||
};
|
||||
|
||||
template <class _IsVector>
|
||||
struct __parallel_tag
|
||||
{
|
||||
using __is_vector = _IsVector;
|
||||
// backend tag can be change depending on
|
||||
// TBB availability in the environment
|
||||
using __backend_tag = __par_backend_tag;
|
||||
};
|
||||
|
||||
template <class _IsVector, class... _IteratorTypes>
|
||||
using __tag_type = typename std::conditional<__internal::__are_random_access_iterators<_IteratorTypes...>::value,
|
||||
__parallel_tag<_IsVector>, __serial_tag<_IsVector>>::type;
|
||||
|
||||
template <class... _IteratorTypes>
|
||||
__serial_tag</*_IsVector = */ std::false_type>
|
||||
__select_backend(__pstl::execution::sequenced_policy, _IteratorTypes&&...)
|
||||
{
|
||||
return {};
|
||||
}
|
||||
|
||||
template <typename _Tp>
|
||||
inline _Tp
|
||||
__lazy_and(_Tp __a, std::true_type)
|
||||
template <class... _IteratorTypes>
|
||||
__serial_tag<__internal::__are_random_access_iterators<_IteratorTypes...>>
|
||||
__select_backend(__pstl::execution::unsequenced_policy, _IteratorTypes&&...)
|
||||
{
|
||||
return __a;
|
||||
return {};
|
||||
}
|
||||
|
||||
template <typename _Tp>
|
||||
std::true_type __lazy_or(_Tp, std::true_type)
|
||||
template <class... _IteratorTypes>
|
||||
__tag_type</*_IsVector = */ std::false_type, _IteratorTypes...>
|
||||
__select_backend(__pstl::execution::parallel_policy, _IteratorTypes&&...)
|
||||
{
|
||||
return std::true_type{};
|
||||
return {};
|
||||
}
|
||||
|
||||
template <typename _Tp>
|
||||
inline _Tp
|
||||
__lazy_or(_Tp __a, std::false_type)
|
||||
template <class... _IteratorTypes>
|
||||
__tag_type<__internal::__are_random_access_iterators<_IteratorTypes...>, _IteratorTypes...>
|
||||
__select_backend(__pstl::execution::parallel_unsequenced_policy, _IteratorTypes&&...)
|
||||
{
|
||||
return __a;
|
||||
return {};
|
||||
}
|
||||
|
||||
/* iterator */
|
||||
template <typename _IteratorType, typename... _OtherIteratorTypes>
|
||||
struct __is_random_access_iterator
|
||||
{
|
||||
static constexpr bool value = __internal::__is_random_access_iterator<_IteratorType>::value &&
|
||||
__internal::__is_random_access_iterator<_OtherIteratorTypes...>::value;
|
||||
typedef std::integral_constant<bool, value> type;
|
||||
};
|
||||
|
||||
template <typename _IteratorType>
|
||||
struct __is_random_access_iterator<_IteratorType>
|
||||
: std::is_same<typename std::iterator_traits<_IteratorType>::iterator_category, std::random_access_iterator_tag>
|
||||
{
|
||||
};
|
||||
|
||||
/* policy */
|
||||
template <typename _Policy>
|
||||
struct __policy_traits
|
||||
{
|
||||
};
|
||||
|
||||
template <>
|
||||
struct __policy_traits<sequenced_policy>
|
||||
{
|
||||
typedef std::false_type allow_parallel;
|
||||
typedef std::false_type allow_unsequenced;
|
||||
typedef std::false_type allow_vector;
|
||||
};
|
||||
|
||||
template <>
|
||||
struct __policy_traits<unsequenced_policy>
|
||||
{
|
||||
typedef std::false_type allow_parallel;
|
||||
typedef std::true_type allow_unsequenced;
|
||||
typedef std::true_type allow_vector;
|
||||
};
|
||||
|
||||
template <>
|
||||
struct __policy_traits<parallel_policy>
|
||||
{
|
||||
typedef std::true_type allow_parallel;
|
||||
typedef std::false_type allow_unsequenced;
|
||||
typedef std::false_type allow_vector;
|
||||
};
|
||||
|
||||
template <>
|
||||
struct __policy_traits<parallel_unsequenced_policy>
|
||||
{
|
||||
typedef std::true_type allow_parallel;
|
||||
typedef std::true_type allow_unsequenced;
|
||||
typedef std::true_type allow_vector;
|
||||
};
|
||||
|
||||
template <typename _ExecutionPolicy>
|
||||
using __collector_t =
|
||||
typename __internal::__policy_traits<typename std::decay<_ExecutionPolicy>::type>::__collector_type;
|
||||
|
||||
template <typename _ExecutionPolicy>
|
||||
using __allow_vector =
|
||||
typename __internal::__policy_traits<typename std::decay<_ExecutionPolicy>::type>::__allow_vector;
|
||||
|
||||
template <typename _ExecutionPolicy>
|
||||
using __allow_unsequenced =
|
||||
typename __internal::__policy_traits<typename std::decay<_ExecutionPolicy>::type>::__allow_unsequenced;
|
||||
|
||||
template <typename _ExecutionPolicy>
|
||||
using __allow_parallel =
|
||||
typename __internal::__policy_traits<typename std::decay<_ExecutionPolicy>::type>::__allow_parallel;
|
||||
|
||||
template <typename _ExecutionPolicy, typename... _IteratorTypes>
|
||||
auto
|
||||
__is_vectorization_preferred(_ExecutionPolicy&& __exec)
|
||||
-> decltype(__internal::__lazy_and(__exec.__allow_vector(),
|
||||
typename __internal::__is_random_access_iterator<_IteratorTypes...>::type()))
|
||||
{
|
||||
return __internal::__lazy_and(__exec.__allow_vector(),
|
||||
typename __internal::__is_random_access_iterator<_IteratorTypes...>::type());
|
||||
}
|
||||
|
||||
template <typename _ExecutionPolicy, typename... _IteratorTypes>
|
||||
auto
|
||||
__is_parallelization_preferred(_ExecutionPolicy&& __exec)
|
||||
-> decltype(__internal::__lazy_and(__exec.__allow_parallel(),
|
||||
typename __internal::__is_random_access_iterator<_IteratorTypes...>::type()))
|
||||
{
|
||||
return __internal::__lazy_and(__exec.__allow_parallel(),
|
||||
typename __internal::__is_random_access_iterator<_IteratorTypes...>::type());
|
||||
}
|
||||
|
||||
template <typename __policy, typename... _IteratorTypes>
|
||||
struct __prefer_unsequenced_tag
|
||||
{
|
||||
static constexpr bool value = __internal::__allow_unsequenced<__policy>::value &&
|
||||
__internal::__is_random_access_iterator<_IteratorTypes...>::value;
|
||||
typedef std::integral_constant<bool, value> type;
|
||||
};
|
||||
|
||||
template <typename __policy, typename... _IteratorTypes>
|
||||
struct __prefer_parallel_tag
|
||||
{
|
||||
static constexpr bool value = __internal::__allow_parallel<__policy>::value &&
|
||||
__internal::__is_random_access_iterator<_IteratorTypes...>::value;
|
||||
typedef std::integral_constant<bool, value> type;
|
||||
};
|
||||
|
||||
} // namespace __internal
|
||||
} // namespace __pstl
|
||||
|
||||
|
|
|
@ -26,10 +26,10 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Predicate>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, bool>
|
||||
any_of(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Predicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_any_of(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_any_of(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__pred);
|
||||
}
|
||||
|
||||
// [alg.all_of]
|
||||
|
@ -56,20 +56,19 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Function>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
||||
for_each(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Function __f)
|
||||
{
|
||||
__pstl::__internal::__pattern_walk1(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __f,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__pattern_walk1(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __f);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Size, class _Function>
|
||||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
for_each_n(_ExecutionPolicy&& __exec, _ForwardIterator __first, _Size __n, _Function __f)
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk1_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __n, __f,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_walk1_n(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
__f);
|
||||
}
|
||||
|
||||
// [alg.find]
|
||||
|
@ -78,10 +77,10 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Predicate>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
find_if(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Predicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_find_if(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_find_if(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Predicate>
|
||||
|
@ -105,12 +104,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
find_end(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __s_first,
|
||||
_ForwardIterator2 __s_last, _BinaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_find_end(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __s_first, __s_last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __s_first);
|
||||
|
||||
return __pstl::__internal::__pattern_find_end(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __s_first, __s_last, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
@ -128,12 +125,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
find_first_of(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last,
|
||||
_ForwardIterator2 __s_first, _ForwardIterator2 __s_last, _BinaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_find_first_of(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __s_first, __s_last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __s_first);
|
||||
|
||||
return __pstl::__internal::__pattern_find_first_of(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __s_first, __s_last, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
@ -150,23 +145,20 @@ template <class _ExecutionPolicy, class _ForwardIterator>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
adjacent_find(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last)
|
||||
{
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
return __pstl::__internal::__pattern_adjacent_find(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, std::equal_to<_ValueType>(),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
/*first_semantic*/ false);
|
||||
return __pstl::__internal::__pattern_adjacent_find(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, std::equal_to<_ValueType>(), /*first_semantic*/ false);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _BinaryPredicate>
|
||||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
adjacent_find(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _BinaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_adjacent_find(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
/*first_semantic*/ false);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
return __pstl::__internal::__pattern_adjacent_find(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __pred, /*first_semantic*/ false);
|
||||
}
|
||||
|
||||
// [alg.count]
|
||||
|
@ -179,12 +171,11 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy,
|
|||
typename iterator_traits<_ForwardIterator>::difference_type>
|
||||
count(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, const _Tp& __value)
|
||||
{
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
return __pstl::__internal::__pattern_count(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[&__value](const _ValueType& __x) { return __value == __x; },
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
return __pstl::__internal::__pattern_count(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[&__value](const _ValueType& __x) { return __value == __x; });
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Predicate>
|
||||
|
@ -192,10 +183,9 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy,
|
|||
typename iterator_traits<_ForwardIterator>::difference_type>
|
||||
count_if(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Predicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_count(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
return __pstl::__internal::__pattern_count(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__pred);
|
||||
}
|
||||
|
||||
// [alg.search]
|
||||
|
@ -205,12 +195,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
search(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __s_first,
|
||||
_ForwardIterator2 __s_last, _BinaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_search(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __s_first, __s_last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __s_first);
|
||||
|
||||
return __pstl::__internal::__pattern_search(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__s_first, __s_last, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
@ -226,10 +214,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
search_n(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Size __count,
|
||||
const _Tp& __value, _BinaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_search_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __count, __value, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_search_n(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __count, __value, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Size, class _Tp>
|
||||
|
@ -247,34 +235,28 @@ template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterato
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator2>
|
||||
copy(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result)
|
||||
{
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__pattern_walk2_brick(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[__is_vector](_ForwardIterator1 __begin, _ForwardIterator1 __end, _ForwardIterator2 __res) {
|
||||
return __pstl::__internal::__brick_copy(__begin, __end, __res, __is_vector);
|
||||
},
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[](_ForwardIterator1 __begin, _ForwardIterator1 __end, _ForwardIterator2 __res)
|
||||
{ return __pstl::__internal::__brick_copy(__begin, __end, __res, __is_vector{}); });
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _Size, class _ForwardIterator2>
|
||||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator2>
|
||||
copy_n(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _Size __n, _ForwardIterator2 __result)
|
||||
{
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__pattern_walk2_brick_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[__is_vector](_ForwardIterator1 __begin, _Size __sz, _ForwardIterator2 __res) {
|
||||
return __pstl::__internal::__brick_copy_n(__begin, __sz, __res, __is_vector);
|
||||
},
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[](_ForwardIterator1 __begin, _Size __sz, _ForwardIterator2 __res)
|
||||
{ return __pstl::__internal::__brick_copy_n(__begin, __sz, __res, __is_vector{}); });
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _Predicate>
|
||||
|
@ -282,12 +264,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
copy_if(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result,
|
||||
_Predicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_copy_if(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_copy_if(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __result, __pred);
|
||||
}
|
||||
|
||||
// [alg.swap]
|
||||
|
@ -299,16 +279,16 @@ swap_ranges(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardItera
|
|||
{
|
||||
typedef typename iterator_traits<_ForwardIterator1>::reference _ReferenceType1;
|
||||
typedef typename iterator_traits<_ForwardIterator2>::reference _ReferenceType2;
|
||||
return __pstl::__internal::__pattern_walk2(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2,
|
||||
[](_ReferenceType1 __x, _ReferenceType2 __y) {
|
||||
using std::swap;
|
||||
swap(__x, __y);
|
||||
},
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2);
|
||||
|
||||
return __pstl::__internal::__pattern_walk2(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1,
|
||||
__last1, __first2,
|
||||
[](_ReferenceType1 __x, _ReferenceType2 __y)
|
||||
{
|
||||
using std::swap;
|
||||
swap(__x, __y);
|
||||
});
|
||||
}
|
||||
|
||||
// [alg.transform]
|
||||
|
@ -320,13 +300,12 @@ transform(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator
|
|||
{
|
||||
typedef typename iterator_traits<_ForwardIterator1>::reference _InputType;
|
||||
typedef typename iterator_traits<_ForwardIterator2>::reference _OutputType;
|
||||
return __pstl::__internal::__pattern_walk2(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[__op](_InputType __x, _OutputType __y) mutable { __y = __op(__x); },
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_walk2(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__result,
|
||||
[__op](_InputType __x, _OutputType __y) mutable { __y = __op(__x); });
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _ForwardIterator,
|
||||
|
@ -338,13 +317,12 @@ transform(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterato
|
|||
typedef typename iterator_traits<_ForwardIterator1>::reference _Input1Type;
|
||||
typedef typename iterator_traits<_ForwardIterator2>::reference _Input2Type;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _OutputType;
|
||||
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_walk3(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __result,
|
||||
[__op](_Input1Type __x, _Input2Type __y, _OutputType __z) mutable { __z = __op(__x, __y); },
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec));
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __result,
|
||||
[__op](_Input1Type __x, _Input2Type __y, _OutputType __z) mutable { __z = __op(__x, __y); });
|
||||
}
|
||||
|
||||
// [alg.replace]
|
||||
|
@ -355,16 +333,17 @@ replace_if(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator
|
|||
const _Tp& __new_value)
|
||||
{
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ElementType;
|
||||
__pstl::__internal::__pattern_walk1(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[&__pred, &__new_value](_ElementType __elem) {
|
||||
if (__pred(__elem))
|
||||
{
|
||||
__elem = __new_value;
|
||||
}
|
||||
},
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__pattern_walk1(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[&__pred, &__new_value](_ElementType __elem)
|
||||
{
|
||||
if (__pred(__elem))
|
||||
{
|
||||
__elem = __new_value;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Tp>
|
||||
|
@ -383,13 +362,12 @@ replace_copy_if(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIt
|
|||
{
|
||||
typedef typename iterator_traits<_ForwardIterator1>::reference _InputType;
|
||||
typedef typename iterator_traits<_ForwardIterator2>::reference _OutputType;
|
||||
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_walk2(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[__pred, &__new_value](_InputType __x, _OutputType __y) mutable { __y = __pred(__x) ? __new_value : __x; },
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[__pred, &__new_value](_InputType __x, _OutputType __y) mutable { __y = __pred(__x) ? __new_value : __x; });
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _Tp>
|
||||
|
@ -407,10 +385,10 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Tp>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
||||
fill(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, const _Tp& __value)
|
||||
{
|
||||
__pstl::__internal::__pattern_fill(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __value,
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__pattern_fill(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__value);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Size, class _Tp>
|
||||
|
@ -420,10 +398,10 @@ fill_n(_ExecutionPolicy&& __exec, _ForwardIterator __first, _Size __count, const
|
|||
if (__count <= 0)
|
||||
return __first;
|
||||
|
||||
return __pstl::__internal::__pattern_fill_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __count, __value,
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_fill_n(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__count, __value);
|
||||
}
|
||||
|
||||
// [alg.generate]
|
||||
|
@ -431,10 +409,10 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Generator>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
||||
generate(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Generator __g)
|
||||
{
|
||||
__pstl::__internal::__pattern_generate(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __g,
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__pattern_generate(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__g);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Size, class _Generator>
|
||||
|
@ -444,10 +422,10 @@ generate_n(_ExecutionPolicy&& __exec, _ForwardIterator __first, _Size __count, _
|
|||
if (__count <= 0)
|
||||
return __first;
|
||||
|
||||
return __pstl::__internal::__pattern_generate_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __count, __g,
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_generate_n(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__count, __g);
|
||||
}
|
||||
|
||||
// [alg.remove]
|
||||
|
@ -473,10 +451,10 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _UnaryPredicate>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
remove_if(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _UnaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_remove_if(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_remove_if(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Tp>
|
||||
|
@ -493,10 +471,10 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _BinaryPredicate
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
unique(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _BinaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_unique(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_unique(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator>
|
||||
|
@ -511,12 +489,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
unique_copy(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __result,
|
||||
_BinaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_unique_copy(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_unique_copy(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __result, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
@ -532,10 +508,9 @@ template <class _ExecutionPolicy, class _BidirectionalIterator>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
||||
reverse(_ExecutionPolicy&& __exec, _BidirectionalIterator __first, _BidirectionalIterator __last)
|
||||
{
|
||||
__pstl::__internal::__pattern_reverse(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _BidirectionalIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _BidirectionalIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__pattern_reverse(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _BidirectionalIterator, class _ForwardIterator>
|
||||
|
@ -543,12 +518,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
reverse_copy(_ExecutionPolicy&& __exec, _BidirectionalIterator __first, _BidirectionalIterator __last,
|
||||
_ForwardIterator __d_first)
|
||||
{
|
||||
return __pstl::__internal::__pattern_reverse_copy(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __d_first,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _BidirectionalIterator, _ForwardIterator>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _BidirectionalIterator, _ForwardIterator>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __d_first);
|
||||
|
||||
return __pstl::__internal::__pattern_reverse_copy(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __d_first);
|
||||
}
|
||||
|
||||
// [alg.rotate]
|
||||
|
@ -557,10 +530,10 @@ template <class _ExecutionPolicy, class _ForwardIterator>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
rotate(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __middle, _ForwardIterator __last)
|
||||
{
|
||||
return __pstl::__internal::__pattern_rotate(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __middle, __last,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_rotate(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__middle, __last);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
@ -568,12 +541,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
rotate_copy(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __middle, _ForwardIterator1 __last,
|
||||
_ForwardIterator2 __result)
|
||||
{
|
||||
return __pstl::__internal::__pattern_rotate_copy(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __middle, __last, __result,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_rotate_copy(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__middle, __last, __result);
|
||||
}
|
||||
|
||||
// [alg.partitions]
|
||||
|
@ -582,20 +553,19 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _UnaryPredicate>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, bool>
|
||||
is_partitioned(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _UnaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_is_partitioned(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
return __pstl::__internal::__pattern_is_partitioned(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _UnaryPredicate>
|
||||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
partition(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _UnaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_partition(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_partition(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _BidirectionalIterator, class _UnaryPredicate>
|
||||
|
@ -603,10 +573,9 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _Bidirectiona
|
|||
stable_partition(_ExecutionPolicy&& __exec, _BidirectionalIterator __first, _BidirectionalIterator __last,
|
||||
_UnaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_stable_partition(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _BidirectionalIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _BidirectionalIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
return __pstl::__internal::__pattern_stable_partition(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first, __last, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _ForwardIterator1, class _ForwardIterator2,
|
||||
|
@ -615,12 +584,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, std::pair<_Fo
|
|||
partition_copy(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last,
|
||||
_ForwardIterator1 __out_true, _ForwardIterator2 __out_false, _UnaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_partition_copy(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __out_true, __out_false, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator, _ForwardIterator1,
|
||||
_ForwardIterator2>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator, _ForwardIterator1,
|
||||
_ForwardIterator2>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __out_true, __out_false);
|
||||
|
||||
return __pstl::__internal::__pattern_partition_copy(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __out_true, __out_false, __pred);
|
||||
}
|
||||
|
||||
// [alg.sort]
|
||||
|
@ -629,12 +596,11 @@ template <class _ExecutionPolicy, class _RandomAccessIterator, class _Compare>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
||||
sort(_ExecutionPolicy&& __exec, _RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
|
||||
{
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
typedef typename iterator_traits<_RandomAccessIterator>::value_type _InputType;
|
||||
return __pstl::__internal::__pattern_sort(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec),
|
||||
typename std::is_move_constructible<_InputType>::type());
|
||||
return __pstl::__internal::__pattern_sort(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__comp, typename std::is_move_constructible<_InputType>::type());
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator>
|
||||
|
@ -651,10 +617,10 @@ template <class _ExecutionPolicy, class _RandomAccessIterator, class _Compare>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
||||
stable_sort(_ExecutionPolicy&& __exec, _RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_stable_sort(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_stable_sort(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator>
|
||||
|
@ -672,12 +638,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, std::pair<_Fo
|
|||
mismatch(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1, _ForwardIterator2 __first2,
|
||||
_ForwardIterator2 __last2, _BinaryPredicate __pred)
|
||||
{
|
||||
return __pstl::__internal::__pattern_mismatch(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __pred,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2);
|
||||
|
||||
return __pstl::__internal::__pattern_mismatch(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1,
|
||||
__last1, __first2, __last2, __pred);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _BinaryPredicate>
|
||||
|
@ -714,10 +678,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, bool>
|
|||
equal(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1, _ForwardIterator2 __first2,
|
||||
_BinaryPredicate __p)
|
||||
{
|
||||
return __pstl::__internal::__pattern_equal(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __p,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2);
|
||||
|
||||
return __pstl::__internal::__pattern_equal(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1,
|
||||
__last1, __first2, __p);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
@ -732,10 +696,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, bool>
|
|||
equal(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1, _ForwardIterator2 __first2,
|
||||
_ForwardIterator2 __last2, _BinaryPredicate __p)
|
||||
{
|
||||
return __pstl::__internal::__pattern_equal(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __p,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2);
|
||||
|
||||
return __pstl::__internal::__pattern_equal(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1,
|
||||
__last1, __first2, __last2, __p);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
@ -751,17 +715,14 @@ template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterato
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator2>
|
||||
move(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __d_first)
|
||||
{
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __d_first);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__pattern_walk2_brick(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __d_first,
|
||||
[__is_vector](_ForwardIterator1 __begin, _ForwardIterator1 __end, _ForwardIterator2 __res) {
|
||||
return __pstl::__internal::__brick_move(__begin, __end, __res, __is_vector);
|
||||
},
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __d_first,
|
||||
[](_ForwardIterator1 __begin, _ForwardIterator1 __end, _ForwardIterator2 __res)
|
||||
{ return __pstl::__internal::__brick_move(__begin, __end, __res, __is_vector{}); });
|
||||
}
|
||||
|
||||
// [partial.sort]
|
||||
|
@ -771,10 +732,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
|||
partial_sort(_ExecutionPolicy&& __exec, _RandomAccessIterator __first, _RandomAccessIterator __middle,
|
||||
_RandomAccessIterator __last, _Compare __comp)
|
||||
{
|
||||
__pstl::__internal::__pattern_partial_sort(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __middle, __last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__pattern_partial_sort(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__middle, __last, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator>
|
||||
|
@ -793,12 +754,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _RandomAccess
|
|||
partial_sort_copy(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last,
|
||||
_RandomAccessIterator __d_first, _RandomAccessIterator __d_last, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_partial_sort_copy(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __d_first, __d_last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator, _RandomAccessIterator>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator, _RandomAccessIterator>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __d_first);
|
||||
|
||||
return __pstl::__internal::__pattern_partial_sort_copy(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first, __last, __d_first, __d_last, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _RandomAccessIterator>
|
||||
|
@ -815,11 +774,11 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Compare>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
is_sorted_until(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
|
||||
{
|
||||
const _ForwardIterator __res = __pstl::__internal::__pattern_adjacent_find(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __pstl::__internal::__reorder_pred<_Compare>(__comp),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
/*first_semantic*/ false);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
const _ForwardIterator __res =
|
||||
__pstl::__internal::__pattern_adjacent_find(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __pstl::__internal::__reorder_pred<_Compare>(__comp),
|
||||
/*first_semantic*/ false);
|
||||
return __res == __last ? __last : std::next(__res);
|
||||
}
|
||||
|
||||
|
@ -835,12 +794,10 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Compare>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, bool>
|
||||
is_sorted(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_adjacent_find(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__pstl::__internal::__reorder_pred<_Compare>(__comp),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
/*or_semantic*/ true) == __last;
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
return __pstl::__internal::__pattern_adjacent_find(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __pstl::__internal::__reorder_pred<_Compare>(__comp),
|
||||
/*or_semantic*/ true) == __last;
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator>
|
||||
|
@ -858,12 +815,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
merge(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1, _ForwardIterator2 __first2,
|
||||
_ForwardIterator2 __last2, _ForwardIterator __d_first, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_merge(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __d_first, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2, __d_first);
|
||||
|
||||
return __pstl::__internal::__pattern_merge(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1,
|
||||
__last1, __first2, __last2, __d_first, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _ForwardIterator>
|
||||
|
@ -880,10 +835,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
|||
inplace_merge(_ExecutionPolicy&& __exec, _BidirectionalIterator __first, _BidirectionalIterator __middle,
|
||||
_BidirectionalIterator __last, _Compare __comp)
|
||||
{
|
||||
__pstl::__internal::__pattern_inplace_merge(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __middle, __last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _BidirectionalIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _BidirectionalIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__pattern_inplace_merge(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__middle, __last, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _BidirectionalIterator>
|
||||
|
@ -902,12 +857,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, bool>
|
|||
includes(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1, _ForwardIterator2 __first2,
|
||||
_ForwardIterator2 __last2, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_includes(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2);
|
||||
|
||||
return __pstl::__internal::__pattern_includes(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1,
|
||||
__last1, __first2, __last2, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
@ -926,12 +879,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
set_union(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1, _ForwardIterator2 __first2,
|
||||
_ForwardIterator2 __last2, _ForwardIterator __result, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_set_union(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __result, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_set_union(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1,
|
||||
__last1, __first2, __last2, __result, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _ForwardIterator>
|
||||
|
@ -951,12 +902,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
set_intersection(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1,
|
||||
_ForwardIterator2 __first2, _ForwardIterator2 __last2, _ForwardIterator __result, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_set_intersection(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __result, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_set_intersection(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first1, __last1, __first2, __last2, __result, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _ForwardIterator>
|
||||
|
@ -976,12 +925,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
set_difference(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1,
|
||||
_ForwardIterator2 __first2, _ForwardIterator2 __last2, _ForwardIterator __result, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_set_difference(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __result, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_set_difference(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first1, __last1, __first2, __last2, __result, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _ForwardIterator>
|
||||
|
@ -1002,12 +949,10 @@ set_symmetric_difference(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1,
|
|||
_ForwardIterator2 __first2, _ForwardIterator2 __last2, _ForwardIterator __result,
|
||||
_Compare __comp)
|
||||
{
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_set_symmetric_difference(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __result, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2,
|
||||
_ForwardIterator>(__exec));
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __result, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _ForwardIterator>
|
||||
|
@ -1024,10 +969,10 @@ template <class _ExecutionPolicy, class _RandomAccessIterator, class _Compare>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _RandomAccessIterator>
|
||||
is_heap_until(_ExecutionPolicy&& __exec, _RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_is_heap_until(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__pattern_is_heap_until(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator>
|
||||
|
@ -1059,10 +1004,9 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Compare>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardIterator>
|
||||
min_element(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_min_element(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
return __pstl::__internal::__pattern_min_element(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator>
|
||||
|
@ -1094,10 +1038,9 @@ template <class _ExecutionPolicy, class _ForwardIterator, class _Compare>
|
|||
__pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, std::pair<_ForwardIterator, _ForwardIterator>>
|
||||
minmax_element(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_minmax_element(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
return __pstl::__internal::__pattern_minmax_element(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator>
|
||||
|
@ -1115,10 +1058,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, void>
|
|||
nth_element(_ExecutionPolicy&& __exec, _RandomAccessIterator __first, _RandomAccessIterator __nth,
|
||||
_RandomAccessIterator __last, _Compare __comp)
|
||||
{
|
||||
__pstl::__internal::__pattern_nth_element(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __nth, __last, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _RandomAccessIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__pattern_nth_element(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __nth,
|
||||
__last, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator>
|
||||
|
@ -1137,12 +1080,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, bool>
|
|||
lexicographical_compare(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1,
|
||||
_ForwardIterator2 __first2, _ForwardIterator2 __last2, _Compare __comp)
|
||||
{
|
||||
return __pstl::__internal::__pattern_lexicographical_compare(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __last2, __comp,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2);
|
||||
|
||||
return __pstl::__internal::__pattern_lexicographical_compare(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first1, __last1, __first2, __last2, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
|
|
@ -18,10 +18,10 @@ namespace std
|
|||
{
|
||||
// Type trait
|
||||
using __pstl::execution::is_execution_policy;
|
||||
#if _PSTL_CPP14_VARIABLE_TEMPLATES_PRESENT
|
||||
# if __INTEL_COMPILER
|
||||
template <class T>
|
||||
constexpr bool is_execution_policy_v = is_execution_policy<T>::value;
|
||||
#if defined(_PSTL_CPP14_VARIABLE_TEMPLATES_PRESENT)
|
||||
# if defined(__INTEL_COMPILER)
|
||||
template <class _Tp>
|
||||
constexpr bool is_execution_policy_v = is_execution_policy<_Tp>::value;
|
||||
# else
|
||||
using __pstl::execution::is_execution_policy_v;
|
||||
# endif
|
||||
|
|
|
@ -13,6 +13,8 @@
|
|||
#include "utils.h"
|
||||
#include "algorithm_fwd.h"
|
||||
|
||||
#include "execution_impl.h"
|
||||
|
||||
namespace std
|
||||
{
|
||||
|
||||
|
@ -27,28 +29,25 @@ uninitialized_copy(_ExecutionPolicy&& __exec, _InputIterator __first, _InputIter
|
|||
typedef typename iterator_traits<_InputIterator>::reference _ReferenceType1;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType2;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _InputIterator, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _InputIterator, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__invoke_if_else(
|
||||
std::integral_constant < bool, std::is_trivial<_ValueType1>::value&& std::is_trivial<_ValueType2>::value > (),
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk2_brick(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[__is_vector](_InputIterator __begin, _InputIterator __end, _ForwardIterator __res) {
|
||||
return __pstl::__internal::__brick_copy(__begin, __end, __res, __is_vector);
|
||||
},
|
||||
__is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[](_InputIterator __begin, _InputIterator __end, _ForwardIterator __res)
|
||||
{ return __pstl::__internal::__brick_copy(__begin, __end, __res, __is_vector{}); });
|
||||
},
|
||||
[&]() {
|
||||
return __pstl::__internal::__pattern_walk2(std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__result,
|
||||
[](_ReferenceType1 __val1, _ReferenceType2 __val2) {
|
||||
::new (std::addressof(__val2)) _ValueType2(__val1);
|
||||
},
|
||||
__is_vector, __is_parallel);
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk2(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __result,
|
||||
[](_ReferenceType1 __val1, _ReferenceType2 __val2)
|
||||
{ ::new (std::addressof(__val2)) _ValueType2(__val1); });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -61,27 +60,25 @@ uninitialized_copy_n(_ExecutionPolicy&& __exec, _InputIterator __first, _Size __
|
|||
typedef typename iterator_traits<_InputIterator>::reference _ReferenceType1;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType2;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _InputIterator, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _InputIterator, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__invoke_if_else(
|
||||
std::integral_constant < bool, std::is_trivial<_ValueType1>::value&& std::is_trivial<_ValueType2>::value > (),
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk2_brick_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[__is_vector](_InputIterator __begin, _Size __sz, _ForwardIterator __res) {
|
||||
return __pstl::__internal::__brick_copy_n(__begin, __sz, __res, __is_vector);
|
||||
},
|
||||
__is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[](_InputIterator __begin, _Size __sz, _ForwardIterator __res)
|
||||
{ return __pstl::__internal::__brick_copy_n(__begin, __sz, __res, __is_vector{}); });
|
||||
},
|
||||
[&]() {
|
||||
return __pstl::__internal::__pattern_walk2_n(std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[](_ReferenceType1 __val1, _ReferenceType2 __val2) {
|
||||
::new (std::addressof(__val2)) _ValueType2(__val1);
|
||||
},
|
||||
__is_vector, __is_parallel);
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk2_n(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first, __n, __result,
|
||||
[](_ReferenceType1 __val1, _ReferenceType2 __val2)
|
||||
{ ::new (std::addressof(__val2)) _ValueType2(__val1); });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -96,28 +93,25 @@ uninitialized_move(_ExecutionPolicy&& __exec, _InputIterator __first, _InputIter
|
|||
typedef typename iterator_traits<_InputIterator>::reference _ReferenceType1;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType2;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _InputIterator, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _InputIterator, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__invoke_if_else(
|
||||
std::integral_constant < bool, std::is_trivial<_ValueType1>::value&& std::is_trivial<_ValueType2>::value > (),
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk2_brick(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[__is_vector](_InputIterator __begin, _InputIterator __end, _ForwardIterator __res) {
|
||||
return __pstl::__internal::__brick_copy(__begin, __end, __res, __is_vector);
|
||||
},
|
||||
__is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[](_InputIterator __begin, _InputIterator __end, _ForwardIterator __res)
|
||||
{ return __pstl::__internal::__brick_copy(__begin, __end, __res, __is_vector{}); });
|
||||
},
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk2(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[](_ReferenceType1 __val1, _ReferenceType2 __val2) {
|
||||
::new (std::addressof(__val2)) _ValueType2(std::move(__val1));
|
||||
},
|
||||
__is_vector, __is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __result,
|
||||
[](_ReferenceType1 __val1, _ReferenceType2 __val2)
|
||||
{ ::new (std::addressof(__val2)) _ValueType2(std::move(__val1)); });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -130,28 +124,25 @@ uninitialized_move_n(_ExecutionPolicy&& __exec, _InputIterator __first, _Size __
|
|||
typedef typename iterator_traits<_InputIterator>::reference _ReferenceType1;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType2;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _InputIterator, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _InputIterator, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__invoke_if_else(
|
||||
std::integral_constant < bool, std::is_trivial<_ValueType1>::value&& std::is_trivial<_ValueType2>::value > (),
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk2_brick_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[__is_vector](_InputIterator __begin, _Size __sz, _ForwardIterator __res) {
|
||||
return __pstl::__internal::__brick_copy_n(__begin, __sz, __res, __is_vector);
|
||||
},
|
||||
__is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[](_InputIterator __begin, _Size __sz, _ForwardIterator __res)
|
||||
{ return __pstl::__internal::__brick_copy_n(__begin, __sz, __res, __is_vector{}); });
|
||||
},
|
||||
[&]() {
|
||||
return __pstl::__internal::__pattern_walk2_n(std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[](_ReferenceType1 __val1, _ReferenceType2 __val2) {
|
||||
::new (std::addressof(__val2))
|
||||
_ValueType2(std::move(__val1));
|
||||
},
|
||||
__is_vector, __is_parallel);
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk2_n(
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n, __result,
|
||||
[](_ReferenceType1 __val1, _ReferenceType2 __val2)
|
||||
{ ::new (std::addressof(__val2)) _ValueType2(std::move(__val1)); });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -164,26 +155,24 @@ uninitialized_fill(_ExecutionPolicy&& __exec, _ForwardIterator __first, _Forward
|
|||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
__pstl::__internal::__invoke_if_else(
|
||||
std::is_arithmetic<_ValueType>(),
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
__pstl::__internal::__pattern_walk_brick(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[&__value, &__is_vector](_ForwardIterator __begin, _ForwardIterator __end) {
|
||||
__pstl::__internal::__brick_fill(__begin, __end, _ValueType(__value), __is_vector);
|
||||
},
|
||||
__is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[&__value](_ForwardIterator __begin, _ForwardIterator __end)
|
||||
{ __pstl::__internal::__brick_fill(__begin, __end, _ValueType(__value), __is_vector{}); });
|
||||
},
|
||||
[&]() {
|
||||
__pstl::__internal::__pattern_walk1(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[&__value](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType(__value); }, __is_vector,
|
||||
__is_parallel);
|
||||
[&]()
|
||||
{
|
||||
__pstl::__internal::__pattern_walk1(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[&__value](_ReferenceType __val)
|
||||
{ ::new (std::addressof(__val)) _ValueType(__value); });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -194,26 +183,24 @@ uninitialized_fill_n(_ExecutionPolicy&& __exec, _ForwardIterator __first, _Size
|
|||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__invoke_if_else(
|
||||
std::is_arithmetic<_ValueType>(),
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk_brick_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[&__value, &__is_vector](_ForwardIterator __begin, _Size __count) {
|
||||
return __pstl::__internal::__brick_fill_n(__begin, __count, _ValueType(__value), __is_vector);
|
||||
},
|
||||
__is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[&__value](_ForwardIterator __begin, _Size __count)
|
||||
{ return __pstl::__internal::__brick_fill_n(__begin, __count, _ValueType(__value), __is_vector{}); });
|
||||
},
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk1_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[&__value](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType(__value); }, __is_vector,
|
||||
__is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[&__value](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType(__value); });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -226,16 +213,15 @@ destroy(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __
|
|||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__invoke_if_not(std::is_trivially_destructible<_ValueType>(), [&]() {
|
||||
__pstl::__internal::__pattern_walk1(std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[](_ReferenceType __val) { __val.~_ValueType(); }, __is_vector,
|
||||
__is_parallel);
|
||||
});
|
||||
__pstl::__internal::__invoke_if_not(std::is_trivially_destructible<_ValueType>(),
|
||||
[&]()
|
||||
{
|
||||
__pstl::__internal::__pattern_walk1(
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[](_ReferenceType __val) { __val.~_ValueType(); });
|
||||
});
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Size>
|
||||
|
@ -245,17 +231,15 @@ destroy_n(_ExecutionPolicy&& __exec, _ForwardIterator __first, _Size __n)
|
|||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__invoke_if_else(
|
||||
std::is_trivially_destructible<_ValueType>(), [&]() { return std::next(__first, __n); },
|
||||
[&]() {
|
||||
return __pstl::__internal::__pattern_walk1_n(std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[](_ReferenceType __val) { __val.~_ValueType(); }, __is_vector,
|
||||
__is_parallel);
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk1_n(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first, __n,
|
||||
[](_ReferenceType __val) { __val.~_ValueType(); });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -268,16 +252,15 @@ uninitialized_default_construct(_ExecutionPolicy&& __exec, _ForwardIterator __fi
|
|||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
__pstl::__internal::__invoke_if_not(std::is_trivial<_ValueType>(), [&]() {
|
||||
__pstl::__internal::__pattern_walk1(std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType; },
|
||||
__is_vector, __is_parallel);
|
||||
});
|
||||
__pstl::__internal::__invoke_if_not(std::is_trivial<_ValueType>(),
|
||||
[&]()
|
||||
{
|
||||
__pstl::__internal::__pattern_walk1(
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType; });
|
||||
});
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Size>
|
||||
|
@ -287,17 +270,15 @@ uninitialized_default_construct_n(_ExecutionPolicy&& __exec, _ForwardIterator __
|
|||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
return __pstl::__internal::__invoke_if_else(
|
||||
std::is_trivial<_ValueType>(), [&]() { return std::next(__first, __n); },
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk1_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType; }, __is_vector, __is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType; });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -310,25 +291,24 @@ uninitialized_value_construct(_ExecutionPolicy&& __exec, _ForwardIterator __firs
|
|||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
__pstl::__internal::__invoke_if_else(
|
||||
std::is_trivial<_ValueType>(),
|
||||
[&]() {
|
||||
__pstl::__internal::__pattern_walk_brick(std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[__is_vector](_ForwardIterator __begin, _ForwardIterator __end) {
|
||||
__pstl::__internal::__brick_fill(__begin, __end, _ValueType(),
|
||||
__is_vector);
|
||||
},
|
||||
__is_parallel);
|
||||
[&]()
|
||||
{
|
||||
__pstl::__internal::__pattern_walk_brick(
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[](_ForwardIterator __begin, _ForwardIterator __end)
|
||||
{ __pstl::__internal::__brick_fill(__begin, __end, _ValueType(), __is_vector{}); });
|
||||
},
|
||||
[&]() {
|
||||
__pstl::__internal::__pattern_walk1(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType(); }, __is_vector, __is_parallel);
|
||||
[&]()
|
||||
{
|
||||
__pstl::__internal::__pattern_walk1(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[](_ReferenceType __val)
|
||||
{ ::new (std::addressof(__val)) _ValueType(); });
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -339,25 +319,24 @@ uninitialized_value_construct_n(_ExecutionPolicy&& __exec, _ForwardIterator __fi
|
|||
typedef typename iterator_traits<_ForwardIterator>::value_type _ValueType;
|
||||
typedef typename iterator_traits<_ForwardIterator>::reference _ReferenceType;
|
||||
|
||||
const auto __is_parallel =
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
const auto __is_vector =
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec);
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
|
||||
using __is_vector = typename decltype(__dispatch_tag)::__is_vector;
|
||||
|
||||
return __pstl::__internal::__invoke_if_else(
|
||||
std::is_trivial<_ValueType>(),
|
||||
[&]() {
|
||||
return __pstl::__internal::__pattern_walk_brick_n(std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[__is_vector](_ForwardIterator __begin, _Size __count) {
|
||||
return __pstl::__internal::__brick_fill_n(
|
||||
__begin, __count, _ValueType(), __is_vector);
|
||||
},
|
||||
__is_parallel);
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk_brick_n(
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[](_ForwardIterator __begin, _Size __count)
|
||||
{ return __pstl::__internal::__brick_fill_n(__begin, __count, _ValueType(), __is_vector{}); });
|
||||
},
|
||||
[&]() {
|
||||
[&]()
|
||||
{
|
||||
return __pstl::__internal::__pattern_walk1_n(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType(); }, __is_vector, __is_parallel);
|
||||
__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __n,
|
||||
[](_ReferenceType __val) { ::new (std::addressof(__val)) _ValueType(); });
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
@ -54,14 +54,12 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _Tp>
|
|||
transform_reduce(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1,
|
||||
_ForwardIterator2 __first2, _Tp __init)
|
||||
{
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2);
|
||||
|
||||
typedef typename iterator_traits<_ForwardIterator1>::value_type _InputType;
|
||||
return __pstl::__internal::__pattern_transform_reduce(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __init, std::plus<_InputType>(),
|
||||
std::multiplies<_InputType>(),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
return __pstl::__internal::__pattern_transform_reduce(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first1, __last1, __first2, __init, std::plus<_InputType>(),
|
||||
std::multiplies<_InputType>());
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _Tp, class _BinaryOperation1,
|
||||
|
@ -70,12 +68,10 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _Tp>
|
|||
transform_reduce(_ExecutionPolicy&& __exec, _ForwardIterator1 __first1, _ForwardIterator1 __last1,
|
||||
_ForwardIterator2 __first2, _Tp __init, _BinaryOperation1 __binary_op1, _BinaryOperation2 __binary_op2)
|
||||
{
|
||||
return __pstl::__internal::__pattern_transform_reduce(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1, __first2, __init, __binary_op1, __binary_op2,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first1, __first2);
|
||||
return __pstl::__internal::__pattern_transform_reduce(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first1, __last1, __first2, __init, __binary_op1,
|
||||
__binary_op2);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Tp, class _BinaryOperation, class _UnaryOperation>
|
||||
|
@ -83,10 +79,9 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _Tp>
|
|||
transform_reduce(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Tp __init,
|
||||
_BinaryOperation __binary_op, _UnaryOperation __unary_op)
|
||||
{
|
||||
return __pstl::__internal::__pattern_transform_reduce(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __init, __binary_op, __unary_op,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator>(__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first);
|
||||
return __pstl::__internal::__pattern_transform_reduce(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first, __last, __init, __binary_op, __unary_op);
|
||||
}
|
||||
|
||||
// [exclusive.scan]
|
||||
|
@ -96,12 +91,12 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
exclusive_scan(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last,
|
||||
_ForwardIterator2 __result, _Tp __init)
|
||||
{
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
using namespace __pstl;
|
||||
return __internal::__pattern_transform_scan(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result, __pstl::__internal::__no_op(), __init,
|
||||
std::plus<_Tp>(), /*inclusive=*/std::false_type(),
|
||||
__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(__exec),
|
||||
__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(__exec));
|
||||
return __internal::__pattern_transform_scan(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__result, __pstl::__internal::__no_op(), __init, std::plus<_Tp>(),
|
||||
/*inclusive=*/std::false_type());
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _Tp, class _BinaryOperation>
|
||||
|
@ -109,12 +104,12 @@ __pstl::__internal::__enable_if_execution_policy<_ExecutionPolicy, _ForwardItera
|
|||
exclusive_scan(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last,
|
||||
_ForwardIterator2 __result, _Tp __init, _BinaryOperation __binary_op)
|
||||
{
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
using namespace __pstl;
|
||||
return __internal::__pattern_transform_scan(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result, __pstl::__internal::__no_op(), __init,
|
||||
__binary_op, /*inclusive=*/std::false_type(),
|
||||
__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(__exec),
|
||||
__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(__exec));
|
||||
return __internal::__pattern_transform_scan(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
__result, __pstl::__internal::__no_op(), __init, __binary_op,
|
||||
/*inclusive=*/std::false_type());
|
||||
}
|
||||
|
||||
// [inclusive.scan]
|
||||
|
@ -156,13 +151,11 @@ transform_exclusive_scan(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _
|
|||
_ForwardIterator2 __result, _Tp __init, _BinaryOperation __binary_op,
|
||||
_UnaryOperation __unary_op)
|
||||
{
|
||||
return __pstl::__internal::__pattern_transform_scan(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result, __unary_op, __init, __binary_op,
|
||||
/*inclusive=*/std::false_type(),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_transform_scan(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __result, __unary_op, __init, __binary_op,
|
||||
/*inclusive=*/std::false_type());
|
||||
}
|
||||
|
||||
// [transform.inclusive.scan]
|
||||
|
@ -174,13 +167,11 @@ transform_inclusive_scan(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _
|
|||
_ForwardIterator2 __result, _BinaryOperation __binary_op, _UnaryOperation __unary_op,
|
||||
_Tp __init)
|
||||
{
|
||||
return __pstl::__internal::__pattern_transform_scan(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __result, __unary_op, __init, __binary_op,
|
||||
/*inclusive=*/std::true_type(),
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __result);
|
||||
|
||||
return __pstl::__internal::__pattern_transform_scan(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first,
|
||||
__last, __result, __unary_op, __init, __binary_op,
|
||||
/*inclusive=*/std::true_type());
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _UnaryOperation,
|
||||
|
@ -213,12 +204,10 @@ adjacent_difference(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _Forwa
|
|||
if (__first == __last)
|
||||
return __d_first;
|
||||
|
||||
return __pstl::__internal::__pattern_adjacent_difference(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last, __d_first, __op,
|
||||
__pstl::__internal::__is_vectorization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec),
|
||||
__pstl::__internal::__is_parallelization_preferred<_ExecutionPolicy, _ForwardIterator1, _ForwardIterator2>(
|
||||
__exec));
|
||||
auto __dispatch_tag = __pstl::__internal::__select_backend(__exec, __first, __d_first);
|
||||
|
||||
return __pstl::__internal::__pattern_adjacent_difference(__dispatch_tag, std::forward<_ExecutionPolicy>(__exec),
|
||||
__first, __last, __d_first, __op);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2>
|
||||
|
|
|
@ -36,13 +36,13 @@ __brick_uninitialized_move(_ForwardIterator __first, _ForwardIterator __last, _O
|
|||
return __result;
|
||||
}
|
||||
|
||||
template <typename _ForwardIterator, typename _OutputIterator>
|
||||
template <typename _RandomAccessIterator, typename _OutputIterator>
|
||||
_OutputIterator
|
||||
__brick_uninitialized_move(_ForwardIterator __first, _ForwardIterator __last, _OutputIterator __result,
|
||||
__brick_uninitialized_move(_RandomAccessIterator __first, _RandomAccessIterator __last, _OutputIterator __result,
|
||||
/*vector=*/std::true_type) noexcept
|
||||
{
|
||||
using __ValueType = typename std::iterator_traits<_OutputIterator>::value_type;
|
||||
using _ReferenceType1 = typename std::iterator_traits<_ForwardIterator>::reference;
|
||||
using _ReferenceType1 = typename std::iterator_traits<_RandomAccessIterator>::reference;
|
||||
using _ReferenceType2 = typename std::iterator_traits<_OutputIterator>::reference;
|
||||
|
||||
return __unseq_backend::__simd_walk_2(
|
||||
|
@ -60,12 +60,12 @@ __brick_destroy(_Iterator __first, _Iterator __last, /*vector*/ std::false_type)
|
|||
__first->~_ValueType();
|
||||
}
|
||||
|
||||
template <typename _Iterator>
|
||||
template <typename _RandomAccessIterator>
|
||||
void
|
||||
__brick_destroy(_Iterator __first, _Iterator __last, /*vector*/ std::true_type) noexcept
|
||||
__brick_destroy(_RandomAccessIterator __first, _RandomAccessIterator __last, /*vector*/ std::true_type) noexcept
|
||||
{
|
||||
using _ValueType = typename std::iterator_traits<_Iterator>::value_type;
|
||||
using _ReferenceType = typename std::iterator_traits<_Iterator>::reference;
|
||||
using _ValueType = typename std::iterator_traits<_RandomAccessIterator>::value_type;
|
||||
using _ReferenceType = typename std::iterator_traits<_RandomAccessIterator>::reference;
|
||||
|
||||
__unseq_backend::__simd_walk_1(__first, __last - __first, [](_ReferenceType __x) { __x.~_ValueType(); });
|
||||
}
|
||||
|
@ -87,13 +87,13 @@ __brick_uninitialized_copy(_ForwardIterator __first, _ForwardIterator __last, _O
|
|||
return __result;
|
||||
}
|
||||
|
||||
template <typename _ForwardIterator, typename _OutputIterator>
|
||||
template <typename _RandomAccessIterator, typename _OutputIterator>
|
||||
_OutputIterator
|
||||
__brick_uninitialized_copy(_ForwardIterator __first, _ForwardIterator __last, _OutputIterator __result,
|
||||
__brick_uninitialized_copy(_RandomAccessIterator __first, _RandomAccessIterator __last, _OutputIterator __result,
|
||||
/*vector=*/std::true_type) noexcept
|
||||
{
|
||||
using __ValueType = typename std::iterator_traits<_OutputIterator>::value_type;
|
||||
using _ReferenceType1 = typename std::iterator_traits<_ForwardIterator>::reference;
|
||||
using _ReferenceType1 = typename std::iterator_traits<_RandomAccessIterator>::reference;
|
||||
using _ReferenceType2 = typename std::iterator_traits<_OutputIterator>::reference;
|
||||
|
||||
return __unseq_backend::__simd_walk_2(
|
||||
|
|
|
@ -22,9 +22,10 @@ namespace __internal
|
|||
// transform_reduce (version with two binary functions, according to draft N4659)
|
||||
//------------------------------------------------------------------------
|
||||
|
||||
template <class _ForwardIterator1, class _ForwardIterator2, class _Tp, class _BinaryOperation1, class _BinaryOperation2>
|
||||
_Tp __brick_transform_reduce(_ForwardIterator1, _ForwardIterator1, _ForwardIterator2, _Tp, _BinaryOperation1,
|
||||
_BinaryOperation2,
|
||||
template <class _RandomAccessIterator1, class _RandomAccessIterator2, class _Tp, class _BinaryOperation1,
|
||||
class _BinaryOperation2>
|
||||
_Tp __brick_transform_reduce(_RandomAccessIterator1, _RandomAccessIterator1, _RandomAccessIterator2, _Tp,
|
||||
_BinaryOperation1, _BinaryOperation2,
|
||||
/*__is_vector=*/std::true_type) noexcept;
|
||||
|
||||
template <class _ForwardIterator1, class _ForwardIterator2, class _Tp, class _BinaryOperation1, class _BinaryOperation2>
|
||||
|
@ -32,45 +33,41 @@ _Tp __brick_transform_reduce(_ForwardIterator1, _ForwardIterator1, _ForwardItera
|
|||
_BinaryOperation2,
|
||||
/*__is_vector=*/std::false_type) noexcept;
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _Tp, class _BinaryOperation1,
|
||||
class _BinaryOperation2, class _IsVector>
|
||||
template <class _Tag, class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _Tp,
|
||||
class _BinaryOperation1, class _BinaryOperation2>
|
||||
_Tp
|
||||
__pattern_transform_reduce(_ExecutionPolicy&&, _ForwardIterator1, _ForwardIterator1, _ForwardIterator2, _Tp,
|
||||
_BinaryOperation1, _BinaryOperation2, _IsVector,
|
||||
/*is_parallel=*/std::false_type) noexcept;
|
||||
__pattern_transform_reduce(_Tag, _ExecutionPolicy&&, _ForwardIterator1, _ForwardIterator1, _ForwardIterator2, _Tp,
|
||||
_BinaryOperation1, _BinaryOperation2) noexcept;
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator1, class _RandomAccessIterator2, class _Tp,
|
||||
class _BinaryOperation1, class _BinaryOperation2, class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator1, class _RandomAccessIterator2,
|
||||
class _Tp, class _BinaryOperation1, class _BinaryOperation2>
|
||||
_Tp
|
||||
__pattern_transform_reduce(_ExecutionPolicy&&, _RandomAccessIterator1, _RandomAccessIterator1, _RandomAccessIterator2,
|
||||
_Tp, _BinaryOperation1, _BinaryOperation2, _IsVector __is_vector,
|
||||
/*is_parallel=*/std::true_type);
|
||||
__pattern_transform_reduce(__parallel_tag<_IsVector>, _ExecutionPolicy&&, _RandomAccessIterator1,
|
||||
_RandomAccessIterator1, _RandomAccessIterator2, _Tp, _BinaryOperation1, _BinaryOperation2);
|
||||
|
||||
//------------------------------------------------------------------------
|
||||
// transform_reduce (version with unary and binary functions)
|
||||
//------------------------------------------------------------------------
|
||||
|
||||
template <class _ForwardIterator, class _Tp, class _UnaryOperation, class _BinaryOperation>
|
||||
_Tp __brick_transform_reduce(_ForwardIterator, _ForwardIterator, _Tp, _BinaryOperation, _UnaryOperation,
|
||||
template <class _RandomAccessIterator, class _Tp, class _UnaryOperation, class _BinaryOperation>
|
||||
_Tp __brick_transform_reduce(_RandomAccessIterator, _RandomAccessIterator, _Tp, _BinaryOperation, _UnaryOperation,
|
||||
/*is_vector=*/std::true_type) noexcept;
|
||||
|
||||
template <class _ForwardIterator, class _Tp, class _BinaryOperation, class _UnaryOperation>
|
||||
_Tp __brick_transform_reduce(_ForwardIterator, _ForwardIterator, _Tp, _BinaryOperation, _UnaryOperation,
|
||||
/*is_vector=*/std::false_type) noexcept;
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Tp, class _BinaryOperation, class _UnaryOperation,
|
||||
class _IsVector>
|
||||
template <class _Tag, class _ExecutionPolicy, class _ForwardIterator, class _Tp, class _BinaryOperation,
|
||||
class _UnaryOperation>
|
||||
_Tp
|
||||
__pattern_transform_reduce(_ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _Tp, _BinaryOperation,
|
||||
_UnaryOperation, _IsVector,
|
||||
/*is_parallel=*/std::false_type) noexcept;
|
||||
__pattern_transform_reduce(_Tag, _ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _Tp, _BinaryOperation,
|
||||
_UnaryOperation) noexcept;
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Tp, class _BinaryOperation, class _UnaryOperation,
|
||||
class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator, class _Tp, class _BinaryOperation,
|
||||
class _UnaryOperation>
|
||||
_Tp
|
||||
__pattern_transform_reduce(_ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _Tp, _BinaryOperation,
|
||||
_UnaryOperation, _IsVector,
|
||||
/*is_parallel=*/std::true_type);
|
||||
__pattern_transform_reduce(__parallel_tag<_IsVector>, _ExecutionPolicy&&, _RandomAccessIterator, _RandomAccessIterator,
|
||||
_Tp, _BinaryOperation, _UnaryOperation);
|
||||
|
||||
//------------------------------------------------------------------------
|
||||
// transform_exclusive_scan
|
||||
|
@ -83,29 +80,28 @@ std::pair<_OutputIterator, _Tp> __brick_transform_scan(_ForwardIterator, _Forwar
|
|||
_UnaryOperation, _Tp, _BinaryOperation,
|
||||
/*Inclusive*/ std::false_type) noexcept;
|
||||
|
||||
template <class _ForwardIterator, class _OutputIterator, class _UnaryOperation, class _Tp, class _BinaryOperation>
|
||||
std::pair<_OutputIterator, _Tp> __brick_transform_scan(_ForwardIterator, _ForwardIterator, _OutputIterator,
|
||||
template <class _RandomAccessIterator, class _OutputIterator, class _UnaryOperation, class _Tp, class _BinaryOperation>
|
||||
std::pair<_OutputIterator, _Tp> __brick_transform_scan(_RandomAccessIterator, _RandomAccessIterator, _OutputIterator,
|
||||
_UnaryOperation, _Tp, _BinaryOperation,
|
||||
/*Inclusive*/ std::true_type) noexcept;
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _UnaryOperation, class _Tp,
|
||||
class _BinaryOperation, class _Inclusive, class _IsVector>
|
||||
template <class _Tag, class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _UnaryOperation,
|
||||
class _Tp, class _BinaryOperation, class _Inclusive>
|
||||
_OutputIterator
|
||||
__pattern_transform_scan(_ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _OutputIterator, _UnaryOperation, _Tp,
|
||||
_BinaryOperation, _Inclusive, _IsVector,
|
||||
/*is_parallel=*/std::false_type) noexcept;
|
||||
__pattern_transform_scan(_Tag, _ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _OutputIterator, _UnaryOperation,
|
||||
_Tp, _BinaryOperation, _Inclusive) noexcept;
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator, class _UnaryOperation, class _Tp,
|
||||
class _BinaryOperation, class _Inclusive, class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator,
|
||||
class _UnaryOperation, class _Tp, class _BinaryOperation, class _Inclusive>
|
||||
typename std::enable_if<!std::is_floating_point<_Tp>::value, _OutputIterator>::type
|
||||
__pattern_transform_scan(_ExecutionPolicy&&, _RandomAccessIterator, _RandomAccessIterator, _OutputIterator,
|
||||
_UnaryOperation, _Tp, _BinaryOperation, _Inclusive, _IsVector, /*is_parallel=*/std::true_type);
|
||||
__pattern_transform_scan(__parallel_tag<_IsVector> __tag, _ExecutionPolicy&&, _RandomAccessIterator,
|
||||
_RandomAccessIterator, _OutputIterator, _UnaryOperation, _Tp, _BinaryOperation, _Inclusive);
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator, class _UnaryOperation, class _Tp,
|
||||
class _BinaryOperation, class _Inclusive, class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator,
|
||||
class _UnaryOperation, class _Tp, class _BinaryOperation, class _Inclusive>
|
||||
typename std::enable_if<std::is_floating_point<_Tp>::value, _OutputIterator>::type
|
||||
__pattern_transform_scan(_ExecutionPolicy&&, _RandomAccessIterator, _RandomAccessIterator, _OutputIterator,
|
||||
_UnaryOperation, _Tp, _BinaryOperation, _Inclusive, _IsVector, /*is_parallel=*/std::true_type);
|
||||
__pattern_transform_scan(__parallel_tag<_IsVector>, _ExecutionPolicy&&, _RandomAccessIterator, _RandomAccessIterator,
|
||||
_OutputIterator, _UnaryOperation, _Tp, _BinaryOperation, _Inclusive);
|
||||
|
||||
//------------------------------------------------------------------------
|
||||
// adjacent_difference
|
||||
|
@ -115,20 +111,20 @@ template <class _ForwardIterator, class _OutputIterator, class _BinaryOperation>
|
|||
_OutputIterator __brick_adjacent_difference(_ForwardIterator, _ForwardIterator, _OutputIterator, _BinaryOperation,
|
||||
/*is_vector*/ std::false_type) noexcept;
|
||||
|
||||
template <class _ForwardIterator, class _OutputIterator, class _BinaryOperation>
|
||||
_OutputIterator __brick_adjacent_difference(_ForwardIterator, _ForwardIterator, _OutputIterator, _BinaryOperation,
|
||||
template <class _RandomAccessIterator, class _OutputIterator, class _BinaryOperation>
|
||||
_OutputIterator __brick_adjacent_difference(_RandomAccessIterator, _RandomAccessIterator, _OutputIterator,
|
||||
_BinaryOperation,
|
||||
/*is_vector*/ std::true_type) noexcept;
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _BinaryOperation,
|
||||
class _IsVector>
|
||||
template <class _Tag, class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _BinaryOperation>
|
||||
_OutputIterator
|
||||
__pattern_adjacent_difference(_ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _OutputIterator, _BinaryOperation,
|
||||
_IsVector, /*is_parallel*/ std::false_type) noexcept;
|
||||
__pattern_adjacent_difference(_Tag, _ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _OutputIterator,
|
||||
_BinaryOperation) noexcept;
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _BinaryOperation,
|
||||
class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator,
|
||||
class _BinaryOperation>
|
||||
_OutputIterator
|
||||
__pattern_adjacent_difference(_ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _OutputIterator, _BinaryOperation,
|
||||
__pattern_adjacent_difference(_ExecutionPolicy&&, _OutputIterator, _OutputIterator, _OutputIterator, _BinaryOperation,
|
||||
_IsVector, /*is_parallel*/ std::true_type);
|
||||
|
||||
} // namespace __internal
|
||||
|
|
|
@ -38,50 +38,56 @@ __brick_transform_reduce(_ForwardIterator1 __first1, _ForwardIterator1 __last1,
|
|||
return std::inner_product(__first1, __last1, __first2, __init, __binary_op1, __binary_op2);
|
||||
}
|
||||
|
||||
template <class _ForwardIterator1, class _ForwardIterator2, class _Tp, class _BinaryOperation1, class _BinaryOperation2>
|
||||
template <class _RandomAccessIterator1, class _RandomAccessIterator2, class _Tp, class _BinaryOperation1,
|
||||
class _BinaryOperation2>
|
||||
_Tp
|
||||
__brick_transform_reduce(_ForwardIterator1 __first1, _ForwardIterator1 __last1, _ForwardIterator2 __first2, _Tp __init,
|
||||
_BinaryOperation1 __binary_op1, _BinaryOperation2 __binary_op2,
|
||||
__brick_transform_reduce(_RandomAccessIterator1 __first1, _RandomAccessIterator1 __last1,
|
||||
_RandomAccessIterator2 __first2, _Tp __init, _BinaryOperation1 __binary_op1,
|
||||
_BinaryOperation2 __binary_op2,
|
||||
/*is_vector=*/std::true_type) noexcept
|
||||
{
|
||||
typedef typename std::iterator_traits<_ForwardIterator1>::difference_type _DifferenceType;
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator1>::difference_type _DifferenceType;
|
||||
return __unseq_backend::__simd_transform_reduce(
|
||||
__last1 - __first1, __init, __binary_op1,
|
||||
[=, &__binary_op2](_DifferenceType __i) { return __binary_op2(__first1[__i], __first2[__i]); });
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _Tp, class _BinaryOperation1,
|
||||
class _BinaryOperation2, class _IsVector>
|
||||
template <class _Tag, class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _Tp,
|
||||
class _BinaryOperation1, class _BinaryOperation2>
|
||||
_Tp
|
||||
__pattern_transform_reduce(_ExecutionPolicy&&, _ForwardIterator1 __first1, _ForwardIterator1 __last1,
|
||||
__pattern_transform_reduce(_Tag, _ExecutionPolicy&&, _ForwardIterator1 __first1, _ForwardIterator1 __last1,
|
||||
_ForwardIterator2 __first2, _Tp __init, _BinaryOperation1 __binary_op1,
|
||||
_BinaryOperation2 __binary_op2, _IsVector __is_vector,
|
||||
/*is_parallel=*/std::false_type) noexcept
|
||||
_BinaryOperation2 __binary_op2) noexcept
|
||||
{
|
||||
return __brick_transform_reduce(__first1, __last1, __first2, __init, __binary_op1, __binary_op2, __is_vector);
|
||||
return __brick_transform_reduce(__first1, __last1, __first2, __init, __binary_op1, __binary_op2,
|
||||
typename _Tag::__is_vector{});
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator1, class _RandomAccessIterator2, class _Tp,
|
||||
class _BinaryOperation1, class _BinaryOperation2, class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator1, class _RandomAccessIterator2,
|
||||
class _Tp, class _BinaryOperation1, class _BinaryOperation2>
|
||||
_Tp
|
||||
__pattern_transform_reduce(_ExecutionPolicy&& __exec, _RandomAccessIterator1 __first1, _RandomAccessIterator1 __last1,
|
||||
_RandomAccessIterator2 __first2, _Tp __init, _BinaryOperation1 __binary_op1,
|
||||
_BinaryOperation2 __binary_op2, _IsVector __is_vector, /*is_parallel=*/std::true_type)
|
||||
__pattern_transform_reduce(__parallel_tag<_IsVector> __tag, _ExecutionPolicy&& __exec, _RandomAccessIterator1 __first1,
|
||||
_RandomAccessIterator1 __last1, _RandomAccessIterator2 __first2, _Tp __init,
|
||||
_BinaryOperation1 __binary_op1, _BinaryOperation2 __binary_op2)
|
||||
{
|
||||
return __internal::__except_handler([&]() {
|
||||
return __par_backend::__parallel_transform_reduce(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first1, __last1,
|
||||
[__first1, __first2, __binary_op2](_RandomAccessIterator1 __i) mutable {
|
||||
return __binary_op2(*__i, *(__first2 + (__i - __first1)));
|
||||
},
|
||||
__init,
|
||||
__binary_op1, // Combine
|
||||
[__first1, __first2, __binary_op1, __binary_op2,
|
||||
__is_vector](_RandomAccessIterator1 __i, _RandomAccessIterator1 __j, _Tp __init) -> _Tp {
|
||||
return __internal::__brick_transform_reduce(__i, __j, __first2 + (__i - __first1), __init, __binary_op1,
|
||||
__binary_op2, __is_vector);
|
||||
});
|
||||
});
|
||||
using __backend_tag = typename decltype(__tag)::__backend_tag;
|
||||
|
||||
return __internal::__except_handler(
|
||||
[&]()
|
||||
{
|
||||
return __par_backend::__parallel_transform_reduce(
|
||||
__backend_tag{}, std::forward<_ExecutionPolicy>(__exec), __first1, __last1,
|
||||
[__first1, __first2, __binary_op2](_RandomAccessIterator1 __i) mutable
|
||||
{ return __binary_op2(*__i, *(__first2 + (__i - __first1))); },
|
||||
__init,
|
||||
__binary_op1, // Combine
|
||||
[__first1, __first2, __binary_op1, __binary_op2](_RandomAccessIterator1 __i, _RandomAccessIterator1 __j,
|
||||
_Tp __init) -> _Tp
|
||||
{
|
||||
return __internal::__brick_transform_reduce(__i, __j, __first2 + (__i - __first1), __init,
|
||||
__binary_op1, __binary_op2, _IsVector{});
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------
|
||||
|
@ -96,42 +102,47 @@ __brick_transform_reduce(_ForwardIterator __first, _ForwardIterator __last, _Tp
|
|||
return std::transform_reduce(__first, __last, __init, __binary_op, __unary_op);
|
||||
}
|
||||
|
||||
template <class _ForwardIterator, class _Tp, class _UnaryOperation, class _BinaryOperation>
|
||||
template <class _RandomAccessIterator, class _Tp, class _UnaryOperation, class _BinaryOperation>
|
||||
_Tp
|
||||
__brick_transform_reduce(_ForwardIterator __first, _ForwardIterator __last, _Tp __init, _BinaryOperation __binary_op,
|
||||
_UnaryOperation __unary_op, /*is_vector=*/std::true_type) noexcept
|
||||
__brick_transform_reduce(_RandomAccessIterator __first, _RandomAccessIterator __last, _Tp __init,
|
||||
_BinaryOperation __binary_op, _UnaryOperation __unary_op,
|
||||
/*is_vector=*/std::true_type) noexcept
|
||||
{
|
||||
typedef typename std::iterator_traits<_ForwardIterator>::difference_type _DifferenceType;
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator>::difference_type _DifferenceType;
|
||||
return __unseq_backend::__simd_transform_reduce(
|
||||
__last - __first, __init, __binary_op,
|
||||
[=, &__unary_op](_DifferenceType __i) { return __unary_op(__first[__i]); });
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Tp, class _BinaryOperation, class _UnaryOperation,
|
||||
class _IsVector>
|
||||
template <class _Tag, class _ExecutionPolicy, class _ForwardIterator, class _Tp, class _BinaryOperation,
|
||||
class _UnaryOperation>
|
||||
_Tp
|
||||
__pattern_transform_reduce(_ExecutionPolicy&&, _ForwardIterator __first, _ForwardIterator __last, _Tp __init,
|
||||
_BinaryOperation __binary_op, _UnaryOperation __unary_op, _IsVector __is_vector,
|
||||
/*is_parallel=*/std::false_type) noexcept
|
||||
__pattern_transform_reduce(_Tag, _ExecutionPolicy&&, _ForwardIterator __first, _ForwardIterator __last, _Tp __init,
|
||||
_BinaryOperation __binary_op, _UnaryOperation __unary_op) noexcept
|
||||
{
|
||||
return __internal::__brick_transform_reduce(__first, __last, __init, __binary_op, __unary_op, __is_vector);
|
||||
return __internal::__brick_transform_reduce(__first, __last, __init, __binary_op, __unary_op,
|
||||
typename _Tag::__is_vector{});
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _Tp, class _BinaryOperation, class _UnaryOperation,
|
||||
class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator, class _Tp, class _BinaryOperation,
|
||||
class _UnaryOperation>
|
||||
_Tp
|
||||
__pattern_transform_reduce(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Tp __init,
|
||||
_BinaryOperation __binary_op, _UnaryOperation __unary_op, _IsVector __is_vector,
|
||||
/*is_parallel=*/std::true_type)
|
||||
__pattern_transform_reduce(__parallel_tag<_IsVector> __tag, _ExecutionPolicy&& __exec, _RandomAccessIterator __first,
|
||||
_RandomAccessIterator __last, _Tp __init, _BinaryOperation __binary_op,
|
||||
_UnaryOperation __unary_op)
|
||||
{
|
||||
return __internal::__except_handler([&]() {
|
||||
return __par_backend::__parallel_transform_reduce(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[__unary_op](_ForwardIterator __i) mutable { return __unary_op(*__i); }, __init, __binary_op,
|
||||
[__unary_op, __binary_op, __is_vector](_ForwardIterator __i, _ForwardIterator __j, _Tp __init) {
|
||||
return __internal::__brick_transform_reduce(__i, __j, __init, __binary_op, __unary_op, __is_vector);
|
||||
});
|
||||
});
|
||||
using __backend_tag = typename decltype(__tag)::__backend_tag;
|
||||
|
||||
return __internal::__except_handler(
|
||||
[&]()
|
||||
{
|
||||
return __par_backend::__parallel_transform_reduce(
|
||||
__backend_tag{}, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[__unary_op](_RandomAccessIterator __i) mutable { return __unary_op(*__i); }, __init, __binary_op,
|
||||
[__unary_op, __binary_op](_RandomAccessIterator __i, _RandomAccessIterator __j, _Tp __init) {
|
||||
return __internal::__brick_transform_reduce(__i, __j, __init, __binary_op, __unary_op, _IsVector{});
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------
|
||||
|
@ -157,9 +168,9 @@ __brick_transform_scan(_ForwardIterator __first, _ForwardIterator __last, _Outpu
|
|||
}
|
||||
|
||||
// Inclusive form
|
||||
template <class _ForwardIterator, class _OutputIterator, class _UnaryOperation, class _Tp, class _BinaryOperation>
|
||||
template <class _RandomAccessIterator, class _OutputIterator, class _UnaryOperation, class _Tp, class _BinaryOperation>
|
||||
std::pair<_OutputIterator, _Tp>
|
||||
__brick_transform_scan(_ForwardIterator __first, _ForwardIterator __last, _OutputIterator __result,
|
||||
__brick_transform_scan(_RandomAccessIterator __first, _RandomAccessIterator __last, _OutputIterator __result,
|
||||
_UnaryOperation __unary_op, _Tp __init, _BinaryOperation __binary_op,
|
||||
/*Inclusive*/ std::true_type, /*is_vector=*/std::false_type) noexcept
|
||||
{
|
||||
|
@ -179,14 +190,14 @@ using is_arithmetic_udop = std::integral_constant<bool, std::is_arithmetic<_Tp>:
|
|||
|
||||
// [restriction] - T shall be DefaultConstructible.
|
||||
// [violation] - default ctor of T shall set the identity value for binary_op.
|
||||
template <class _ForwardIterator, class _OutputIterator, class _UnaryOperation, class _Tp, class _BinaryOperation,
|
||||
template <class _RandomAccessIterator, class _OutputIterator, class _UnaryOperation, class _Tp, class _BinaryOperation,
|
||||
class _Inclusive>
|
||||
typename std::enable_if<!is_arithmetic_udop<_Tp, _BinaryOperation>::value, std::pair<_OutputIterator, _Tp>>::type
|
||||
__brick_transform_scan(_ForwardIterator __first, _ForwardIterator __last, _OutputIterator __result,
|
||||
__brick_transform_scan(_RandomAccessIterator __first, _RandomAccessIterator __last, _OutputIterator __result,
|
||||
_UnaryOperation __unary_op, _Tp __init, _BinaryOperation __binary_op, _Inclusive,
|
||||
/*is_vector=*/std::true_type) noexcept
|
||||
{
|
||||
#if (_PSTL_UDS_PRESENT)
|
||||
#if defined(_PSTL_UDS_PRESENT)
|
||||
return __unseq_backend::__simd_scan(__first, __last - __first, __result, __unary_op, __init, __binary_op,
|
||||
_Inclusive());
|
||||
#else
|
||||
|
@ -196,10 +207,10 @@ __brick_transform_scan(_ForwardIterator __first, _ForwardIterator __last, _Outpu
|
|||
#endif
|
||||
}
|
||||
|
||||
template <class _ForwardIterator, class _OutputIterator, class _UnaryOperation, class _Tp, class _BinaryOperation,
|
||||
template <class _RandomAccessIterator, class _OutputIterator, class _UnaryOperation, class _Tp, class _BinaryOperation,
|
||||
class _Inclusive>
|
||||
typename std::enable_if<is_arithmetic_udop<_Tp, _BinaryOperation>::value, std::pair<_OutputIterator, _Tp>>::type
|
||||
__brick_transform_scan(_ForwardIterator __first, _ForwardIterator __last, _OutputIterator __result,
|
||||
__brick_transform_scan(_RandomAccessIterator __first, _RandomAccessIterator __last, _OutputIterator __result,
|
||||
_UnaryOperation __unary_op, _Tp __init, _BinaryOperation __binary_op, _Inclusive,
|
||||
/*is_vector=*/std::true_type) noexcept
|
||||
{
|
||||
|
@ -207,55 +218,62 @@ __brick_transform_scan(_ForwardIterator __first, _ForwardIterator __last, _Outpu
|
|||
/*is_vector=*/std::false_type());
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _UnaryOperation, class _Tp,
|
||||
class _BinaryOperation, class _Inclusive, class _IsVector>
|
||||
template <class _Tag, class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _UnaryOperation,
|
||||
class _Tp, class _BinaryOperation, class _Inclusive>
|
||||
_OutputIterator
|
||||
__pattern_transform_scan(_ExecutionPolicy&&, _ForwardIterator __first, _ForwardIterator __last,
|
||||
__pattern_transform_scan(_Tag, _ExecutionPolicy&&, _ForwardIterator __first, _ForwardIterator __last,
|
||||
_OutputIterator __result, _UnaryOperation __unary_op, _Tp __init, _BinaryOperation __binary_op,
|
||||
_Inclusive, _IsVector __is_vector, /*is_parallel=*/std::false_type) noexcept
|
||||
_Inclusive) noexcept
|
||||
{
|
||||
return __internal::__brick_transform_scan(__first, __last, __result, __unary_op, __init, __binary_op, _Inclusive(),
|
||||
__is_vector)
|
||||
typename _Tag::__is_vector{})
|
||||
.first;
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator, class _UnaryOperation, class _Tp,
|
||||
class _BinaryOperation, class _Inclusive, class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator,
|
||||
class _UnaryOperation, class _Tp, class _BinaryOperation, class _Inclusive>
|
||||
typename std::enable_if<!std::is_floating_point<_Tp>::value, _OutputIterator>::type
|
||||
__pattern_transform_scan(_ExecutionPolicy&& __exec, _RandomAccessIterator __first, _RandomAccessIterator __last,
|
||||
_OutputIterator __result, _UnaryOperation __unary_op, _Tp __init, _BinaryOperation __binary_op,
|
||||
_Inclusive, _IsVector __is_vector, /*is_parallel=*/std::true_type)
|
||||
__pattern_transform_scan(__parallel_tag<_IsVector> __tag, _ExecutionPolicy&& __exec, _RandomAccessIterator __first,
|
||||
_RandomAccessIterator __last, _OutputIterator __result, _UnaryOperation __unary_op, _Tp __init,
|
||||
_BinaryOperation __binary_op, _Inclusive)
|
||||
{
|
||||
using __backend_tag = typename decltype(__tag)::__backend_tag;
|
||||
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator>::difference_type _DifferenceType;
|
||||
|
||||
return __internal::__except_handler([&]() {
|
||||
__par_backend::__parallel_transform_scan(
|
||||
std::forward<_ExecutionPolicy>(__exec), __last - __first,
|
||||
[__first, __unary_op](_DifferenceType __i) mutable { return __unary_op(__first[__i]); }, __init,
|
||||
__binary_op,
|
||||
[__first, __unary_op, __binary_op](_DifferenceType __i, _DifferenceType __j, _Tp __init) {
|
||||
// Execute serial __brick_transform_reduce, due to the explicit SIMD vectorization (reduction) requires a commutative operation for the guarantee of correct scan.
|
||||
return __internal::__brick_transform_reduce(__first + __i, __first + __j, __init, __binary_op,
|
||||
__unary_op,
|
||||
/*__is_vector*/ std::false_type());
|
||||
},
|
||||
[__first, __unary_op, __binary_op, __result, __is_vector](_DifferenceType __i, _DifferenceType __j,
|
||||
_Tp __init) {
|
||||
return __internal::__brick_transform_scan(__first + __i, __first + __j, __result + __i, __unary_op,
|
||||
__init, __binary_op, _Inclusive(), __is_vector)
|
||||
.second;
|
||||
});
|
||||
return __result + (__last - __first);
|
||||
});
|
||||
return __internal::__except_handler(
|
||||
[&]()
|
||||
{
|
||||
__par_backend::__parallel_transform_scan(
|
||||
__backend_tag{}, std::forward<_ExecutionPolicy>(__exec), __last - __first,
|
||||
[__first, __unary_op](_DifferenceType __i) mutable { return __unary_op(__first[__i]); }, __init,
|
||||
__binary_op,
|
||||
[__first, __unary_op, __binary_op](_DifferenceType __i, _DifferenceType __j, _Tp __init)
|
||||
{
|
||||
// Execute serial __brick_transform_reduce, due to the explicit SIMD vectorization (reduction) requires a commutative operation for the guarantee of correct scan.
|
||||
return __internal::__brick_transform_reduce(__first + __i, __first + __j, __init, __binary_op,
|
||||
__unary_op,
|
||||
/*__is_vector*/ std::false_type());
|
||||
},
|
||||
[__first, __unary_op, __binary_op, __result](_DifferenceType __i, _DifferenceType __j, _Tp __init)
|
||||
{
|
||||
return __internal::__brick_transform_scan(__first + __i, __first + __j, __result + __i, __unary_op,
|
||||
__init, __binary_op, _Inclusive(), _IsVector{})
|
||||
.second;
|
||||
});
|
||||
return __result + (__last - __first);
|
||||
});
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator, class _UnaryOperation, class _Tp,
|
||||
class _BinaryOperation, class _Inclusive, class _IsVector>
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator, class _OutputIterator,
|
||||
class _UnaryOperation, class _Tp, class _BinaryOperation, class _Inclusive>
|
||||
typename std::enable_if<std::is_floating_point<_Tp>::value, _OutputIterator>::type
|
||||
__pattern_transform_scan(_ExecutionPolicy&& __exec, _RandomAccessIterator __first, _RandomAccessIterator __last,
|
||||
_OutputIterator __result, _UnaryOperation __unary_op, _Tp __init, _BinaryOperation __binary_op,
|
||||
_Inclusive, _IsVector __is_vector, /*is_parallel=*/std::true_type)
|
||||
__pattern_transform_scan(__parallel_tag<_IsVector> __tag, _ExecutionPolicy&& __exec, _RandomAccessIterator __first,
|
||||
_RandomAccessIterator __last, _OutputIterator __result, _UnaryOperation __unary_op, _Tp __init,
|
||||
_BinaryOperation __binary_op, _Inclusive)
|
||||
{
|
||||
using __backend_tag = typename decltype(__tag)::__backend_tag;
|
||||
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator>::difference_type _DifferenceType;
|
||||
_DifferenceType __n = __last - __first;
|
||||
|
||||
|
@ -263,26 +281,31 @@ __pattern_transform_scan(_ExecutionPolicy&& __exec, _RandomAccessIterator __firs
|
|||
{
|
||||
return __result;
|
||||
}
|
||||
return __internal::__except_handler([&]() {
|
||||
__par_backend::__parallel_strict_scan(
|
||||
std::forward<_ExecutionPolicy>(__exec), __n, __init,
|
||||
[__first, __unary_op, __binary_op, __result, __is_vector](_DifferenceType __i, _DifferenceType __len) {
|
||||
return __internal::__brick_transform_scan(__first + __i, __first + (__i + __len), __result + __i,
|
||||
__unary_op, _Tp{}, __binary_op, _Inclusive(), __is_vector)
|
||||
.second;
|
||||
},
|
||||
__binary_op,
|
||||
[__result, &__binary_op](_DifferenceType __i, _DifferenceType __len, _Tp __initial) {
|
||||
return *(std::transform(__result + __i, __result + __i + __len, __result + __i,
|
||||
[&__initial, &__binary_op](const _Tp& __x) {
|
||||
_PSTL_PRAGMA_FORCEINLINE
|
||||
return __binary_op(__initial, __x);
|
||||
}) -
|
||||
1);
|
||||
},
|
||||
[](_Tp) {});
|
||||
return __result + (__last - __first);
|
||||
});
|
||||
return __internal::__except_handler(
|
||||
[&]()
|
||||
{
|
||||
__par_backend::__parallel_strict_scan(
|
||||
__backend_tag{}, std::forward<_ExecutionPolicy>(__exec), __n, __init,
|
||||
[__first, __unary_op, __binary_op, __result](_DifferenceType __i, _DifferenceType __len)
|
||||
{
|
||||
return __internal::__brick_transform_scan(__first + __i, __first + (__i + __len), __result + __i,
|
||||
__unary_op, _Tp{}, __binary_op, _Inclusive(), _IsVector{})
|
||||
.second;
|
||||
},
|
||||
__binary_op,
|
||||
[__result, &__binary_op](_DifferenceType __i, _DifferenceType __len, _Tp __initial)
|
||||
{
|
||||
return *(std::transform(__result + __i, __result + __i + __len, __result + __i,
|
||||
[&__initial, &__binary_op](const _Tp& __x)
|
||||
{
|
||||
_PSTL_PRAGMA_FORCEINLINE
|
||||
return __binary_op(__initial, __x);
|
||||
}) -
|
||||
1);
|
||||
},
|
||||
[](_Tp) {});
|
||||
return __result + (__last - __first);
|
||||
});
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------
|
||||
|
@ -297,15 +320,16 @@ __brick_adjacent_difference(_ForwardIterator __first, _ForwardIterator __last, _
|
|||
return std::adjacent_difference(__first, __last, __d_first, __op);
|
||||
}
|
||||
|
||||
template <class _ForwardIterator1, class _ForwardIterator2, class _BinaryOperation>
|
||||
_ForwardIterator2
|
||||
__brick_adjacent_difference(_ForwardIterator1 __first, _ForwardIterator1 __last, _ForwardIterator2 __d_first,
|
||||
_BinaryOperation __op, /*is_vector=*/std::true_type) noexcept
|
||||
template <class _RandomAccessIterator1, class _RandomAccessIterator2, class _BinaryOperation>
|
||||
_RandomAccessIterator2
|
||||
__brick_adjacent_difference(_RandomAccessIterator1 __first, _RandomAccessIterator1 __last,
|
||||
_RandomAccessIterator2 __d_first, _BinaryOperation __op,
|
||||
/*is_vector=*/std::true_type) noexcept
|
||||
{
|
||||
_PSTL_ASSERT(__first != __last);
|
||||
|
||||
typedef typename std::iterator_traits<_ForwardIterator1>::reference _ReferenceType1;
|
||||
typedef typename std::iterator_traits<_ForwardIterator2>::reference _ReferenceType2;
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator1>::reference _ReferenceType1;
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator2>::reference _ReferenceType2;
|
||||
|
||||
auto __n = __last - __first;
|
||||
*__d_first = *__first;
|
||||
|
@ -314,37 +338,38 @@ __brick_adjacent_difference(_ForwardIterator1 __first, _ForwardIterator1 __last,
|
|||
[&__op](_ReferenceType1 __x, _ReferenceType1 __y, _ReferenceType2 __z) { __z = __op(__x, __y); });
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _BinaryOperation,
|
||||
class _IsVector>
|
||||
template <class _Tag, class _ExecutionPolicy, class _ForwardIterator, class _OutputIterator, class _BinaryOperation>
|
||||
_OutputIterator
|
||||
__pattern_adjacent_difference(_ExecutionPolicy&&, _ForwardIterator __first, _ForwardIterator __last,
|
||||
_OutputIterator __d_first, _BinaryOperation __op, _IsVector __is_vector,
|
||||
/*is_parallel*/ std::false_type) noexcept
|
||||
__pattern_adjacent_difference(_Tag, _ExecutionPolicy&&, _ForwardIterator __first, _ForwardIterator __last,
|
||||
_OutputIterator __d_first, _BinaryOperation __op) noexcept
|
||||
{
|
||||
return __internal::__brick_adjacent_difference(__first, __last, __d_first, __op, __is_vector);
|
||||
return __internal::__brick_adjacent_difference(__first, __last, __d_first, __op, typename _Tag::__is_vector{});
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _ForwardIterator1, class _ForwardIterator2, class _BinaryOperation,
|
||||
class _IsVector>
|
||||
_ForwardIterator2
|
||||
__pattern_adjacent_difference(_ExecutionPolicy&& __exec, _ForwardIterator1 __first, _ForwardIterator1 __last,
|
||||
_ForwardIterator2 __d_first, _BinaryOperation __op, _IsVector __is_vector,
|
||||
/*is_parallel=*/std::true_type)
|
||||
template <class _IsVector, class _ExecutionPolicy, class _RandomAccessIterator1, class _RandomAccessIterator2,
|
||||
class _BinaryOperation>
|
||||
_RandomAccessIterator2
|
||||
__pattern_adjacent_difference(__parallel_tag<_IsVector> __tag, _ExecutionPolicy&& __exec,
|
||||
_RandomAccessIterator1 __first, _RandomAccessIterator1 __last,
|
||||
_RandomAccessIterator2 __d_first, _BinaryOperation __op)
|
||||
{
|
||||
_PSTL_ASSERT(__first != __last);
|
||||
typedef typename std::iterator_traits<_ForwardIterator1>::reference _ReferenceType1;
|
||||
typedef typename std::iterator_traits<_ForwardIterator2>::reference _ReferenceType2;
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator1>::reference _ReferenceType1;
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator2>::reference _ReferenceType2;
|
||||
|
||||
using __backend_tag = typename decltype(__tag)::__backend_tag;
|
||||
|
||||
*__d_first = *__first;
|
||||
__par_backend::__parallel_for(
|
||||
std::forward<_ExecutionPolicy>(__exec), __first, __last - 1,
|
||||
[&__op, __is_vector, __d_first, __first](_ForwardIterator1 __b, _ForwardIterator1 __e) {
|
||||
_ForwardIterator2 __d_b = __d_first + (__b - __first);
|
||||
__internal::__brick_walk3(
|
||||
__b, __e, __b + 1, __d_b + 1,
|
||||
[&__op](_ReferenceType1 __x, _ReferenceType1 __y, _ReferenceType2 __z) { __z = __op(__y, __x); },
|
||||
__is_vector);
|
||||
});
|
||||
__par_backend::__parallel_for(__backend_tag{}, std::forward<_ExecutionPolicy>(__exec), __first, __last - 1,
|
||||
[&__op, __d_first, __first](_RandomAccessIterator1 __b, _RandomAccessIterator1 __e)
|
||||
{
|
||||
_RandomAccessIterator2 __d_b = __d_first + (__b - __first);
|
||||
__internal::__brick_walk3(
|
||||
__b, __e, __b + 1, __d_b + 1,
|
||||
[&__op](_ReferenceType1 __x, _ReferenceType1 __y, _ReferenceType2 __z)
|
||||
{ __z = __op(__y, __x); },
|
||||
_IsVector{});
|
||||
});
|
||||
return __d_first + (__last - __first);
|
||||
}
|
||||
|
||||
|
|
|
@ -22,6 +22,12 @@ namespace __pstl
|
|||
{
|
||||
namespace __par_backend = __tbb_backend;
|
||||
}
|
||||
#elif defined(_PSTL_PAR_BACKEND_OPENMP)
|
||||
# include "parallel_backend_omp.h"
|
||||
namespace __pstl
|
||||
{
|
||||
namespace __par_backend = __omp_backend;
|
||||
}
|
||||
#else
|
||||
_PSTL_PRAGMA_MESSAGE("Parallel backend was not specified");
|
||||
#endif
|
||||
|
|
|
@ -50,15 +50,15 @@ __cancel_execution()
|
|||
|
||||
template <class _ExecutionPolicy, class _Index, class _Fp>
|
||||
void
|
||||
__parallel_for(_ExecutionPolicy&&, _Index __first, _Index __last, _Fp __f)
|
||||
__parallel_for(__pstl::__internal::__serial_backend_tag, _ExecutionPolicy&&, _Index __first, _Index __last, _Fp __f)
|
||||
{
|
||||
__f(__first, __last);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, class _Value, class _Index, typename _RealBody, typename _Reduction>
|
||||
_Value
|
||||
__parallel_reduce(_ExecutionPolicy&&, _Index __first, _Index __last, const _Value& __identity,
|
||||
const _RealBody& __real_body, const _Reduction&)
|
||||
__parallel_reduce(__pstl::__internal::__serial_backend_tag, _ExecutionPolicy&&, _Index __first, _Index __last,
|
||||
const _Value& __identity, const _RealBody& __real_body, const _Reduction&)
|
||||
{
|
||||
if (__first == __last)
|
||||
{
|
||||
|
@ -72,16 +72,16 @@ __parallel_reduce(_ExecutionPolicy&&, _Index __first, _Index __last, const _Valu
|
|||
|
||||
template <class _ExecutionPolicy, class _Index, class _UnaryOp, class _Tp, class _BinaryOp, class _Reduce>
|
||||
_Tp
|
||||
__parallel_transform_reduce(_ExecutionPolicy&&, _Index __first, _Index __last, _UnaryOp, _Tp __init, _BinaryOp,
|
||||
_Reduce __reduce)
|
||||
__parallel_transform_reduce(__pstl::__internal::__serial_backend_tag, _ExecutionPolicy&&, _Index __first, _Index __last,
|
||||
_UnaryOp, _Tp __init, _BinaryOp, _Reduce __reduce)
|
||||
{
|
||||
return __reduce(__first, __last, __init);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, typename _Index, typename _Tp, typename _Rp, typename _Cp, typename _Sp, typename _Ap>
|
||||
void
|
||||
__parallel_strict_scan(_ExecutionPolicy&&, _Index __n, _Tp __initial, _Rp __reduce, _Cp __combine, _Sp __scan,
|
||||
_Ap __apex)
|
||||
__parallel_strict_scan(__pstl::__internal::__serial_backend_tag, _ExecutionPolicy&&, _Index __n, _Tp __initial,
|
||||
_Rp __reduce, _Cp __combine, _Sp __scan, _Ap __apex)
|
||||
{
|
||||
_Tp __sum = __initial;
|
||||
if (__n)
|
||||
|
@ -93,15 +93,16 @@ __parallel_strict_scan(_ExecutionPolicy&&, _Index __n, _Tp __initial, _Rp __redu
|
|||
|
||||
template <class _ExecutionPolicy, class _Index, class _UnaryOp, class _Tp, class _BinaryOp, class _Reduce, class _Scan>
|
||||
_Tp
|
||||
__parallel_transform_scan(_ExecutionPolicy&&, _Index __n, _UnaryOp, _Tp __init, _BinaryOp, _Reduce, _Scan __scan)
|
||||
__parallel_transform_scan(__pstl::__internal::__serial_backend_tag, _ExecutionPolicy&&, _Index __n, _UnaryOp,
|
||||
_Tp __init, _BinaryOp, _Reduce, _Scan __scan)
|
||||
{
|
||||
return __scan(_Index(0), __n, __init);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, typename _RandomAccessIterator, typename _Compare, typename _LeafSort>
|
||||
void
|
||||
__parallel_stable_sort(_ExecutionPolicy&&, _RandomAccessIterator __first, _RandomAccessIterator __last, _Compare __comp,
|
||||
_LeafSort __leaf_sort, std::size_t = 0)
|
||||
__parallel_stable_sort(__pstl::__internal::__serial_backend_tag, _ExecutionPolicy&&, _RandomAccessIterator __first,
|
||||
_RandomAccessIterator __last, _Compare __comp, _LeafSort __leaf_sort, std::size_t = 0)
|
||||
{
|
||||
__leaf_sort(__first, __last, __comp);
|
||||
}
|
||||
|
@ -109,16 +110,16 @@ __parallel_stable_sort(_ExecutionPolicy&&, _RandomAccessIterator __first, _Rando
|
|||
template <class _ExecutionPolicy, typename _RandomAccessIterator1, typename _RandomAccessIterator2,
|
||||
typename _RandomAccessIterator3, typename _Compare, typename _LeafMerge>
|
||||
void
|
||||
__parallel_merge(_ExecutionPolicy&&, _RandomAccessIterator1 __first1, _RandomAccessIterator1 __last1,
|
||||
_RandomAccessIterator2 __first2, _RandomAccessIterator2 __last2, _RandomAccessIterator3 __outit,
|
||||
_Compare __comp, _LeafMerge __leaf_merge)
|
||||
__parallel_merge(__pstl::__internal::__serial_backend_tag, _ExecutionPolicy&&, _RandomAccessIterator1 __first1,
|
||||
_RandomAccessIterator1 __last1, _RandomAccessIterator2 __first2, _RandomAccessIterator2 __last2,
|
||||
_RandomAccessIterator3 __outit, _Compare __comp, _LeafMerge __leaf_merge)
|
||||
{
|
||||
__leaf_merge(__first1, __last1, __first2, __last2, __outit, __comp);
|
||||
}
|
||||
|
||||
template <class _ExecutionPolicy, typename _F1, typename _F2>
|
||||
void
|
||||
__parallel_invoke(_ExecutionPolicy&&, _F1&& __f1, _F2&& __f2)
|
||||
__parallel_invoke(__pstl::__internal::__serial_backend_tag, _ExecutionPolicy&&, _F1&& __f1, _F2&& __f2)
|
||||
{
|
||||
std::forward<_F1>(__f1)();
|
||||
std::forward<_F2>(__f2)();
|
||||
|
|
|
@ -99,7 +99,7 @@ class __parallel_for_body
|
|||
// wrapper over tbb::parallel_for
|
||||
template <class _ExecutionPolicy, class _Index, class _Fp>
|
||||
void
|
||||
__parallel_for(_ExecutionPolicy&&, _Index __first, _Index __last, _Fp __f)
|
||||
__parallel_for(__pstl::__internal::__tbb_backend_tag, _ExecutionPolicy&&, _Index __first, _Index __last, _Fp __f)
|
||||
{
|
||||
tbb::this_task_arena::isolate([=]() {
|
||||
tbb::parallel_for(tbb::blocked_range<_Index>(__first, __last), __parallel_for_body<_Index, _Fp>(__f));
|
||||
|
@ -110,8 +110,8 @@ __parallel_for(_ExecutionPolicy&&, _Index __first, _Index __last, _Fp __f)
|
|||
// wrapper over tbb::parallel_reduce
|
||||
template <class _ExecutionPolicy, class _Value, class _Index, typename _RealBody, typename _Reduction>
|
||||
_Value
|
||||
__parallel_reduce(_ExecutionPolicy&&, _Index __first, _Index __last, const _Value& __identity,
|
||||
const _RealBody& __real_body, const _Reduction& __reduction)
|
||||
__parallel_reduce(__pstl::__internal::__tbb_backend_tag, _ExecutionPolicy&&, _Index __first, _Index __last,
|
||||
const _Value& __identity, const _RealBody& __real_body, const _Reduction& __reduction)
|
||||
{
|
||||
return tbb::this_task_arena::isolate([__first, __last, &__identity, &__real_body, &__reduction]() -> _Value {
|
||||
return tbb::parallel_reduce(
|
||||
|
@ -191,8 +191,8 @@ struct __par_trans_red_body
|
|||
|
||||
template <class _ExecutionPolicy, class _Index, class _Up, class _Tp, class _Cp, class _Rp>
|
||||
_Tp
|
||||
__parallel_transform_reduce(_ExecutionPolicy&&, _Index __first, _Index __last, _Up __u, _Tp __init, _Cp __combine,
|
||||
_Rp __brick_reduce)
|
||||
__parallel_transform_reduce(__pstl::__internal::__tbb_backend_tag, _ExecutionPolicy&&, _Index __first, _Index __last,
|
||||
_Up __u, _Tp __init, _Cp __combine, _Rp __brick_reduce)
|
||||
{
|
||||
__tbb_backend::__par_trans_red_body<_Index, _Up, _Tp, _Cp, _Rp> __body(__u, __init, __combine, __brick_reduce);
|
||||
// The grain size of 3 is used in order to provide mininum 2 elements for each body
|
||||
|
@ -354,8 +354,8 @@ __downsweep(_Index __i, _Index __m, _Index __tilesize, _Tp* __r, _Index __lastsi
|
|||
// T must have a trivial constructor and destructor.
|
||||
template <class _ExecutionPolicy, typename _Index, typename _Tp, typename _Rp, typename _Cp, typename _Sp, typename _Ap>
|
||||
void
|
||||
__parallel_strict_scan(_ExecutionPolicy&&, _Index __n, _Tp __initial, _Rp __reduce, _Cp __combine, _Sp __scan,
|
||||
_Ap __apex)
|
||||
__parallel_strict_scan(__pstl::__internal::__tbb_backend_tag, _ExecutionPolicy&&, _Index __n, _Tp __initial,
|
||||
_Rp __reduce, _Cp __combine, _Sp __scan, _Ap __apex)
|
||||
{
|
||||
tbb::this_task_arena::isolate([=, &__combine]() {
|
||||
if (__n > 1)
|
||||
|
@ -394,8 +394,8 @@ __parallel_strict_scan(_ExecutionPolicy&&, _Index __n, _Tp __initial, _Rp __redu
|
|||
|
||||
template <class _ExecutionPolicy, class _Index, class _Up, class _Tp, class _Cp, class _Rp, class _Sp>
|
||||
_Tp
|
||||
__parallel_transform_scan(_ExecutionPolicy&&, _Index __n, _Up __u, _Tp __init, _Cp __combine, _Rp __brick_reduce,
|
||||
_Sp __scan)
|
||||
__parallel_transform_scan(__pstl::__internal::__tbb_backend_tag, _ExecutionPolicy&&, _Index __n, _Up __u, _Tp __init,
|
||||
_Cp __combine, _Rp __brick_reduce, _Sp __scan)
|
||||
{
|
||||
__trans_scan_body<_Index, _Up, _Tp, _Cp, _Rp, _Sp> __body(__u, __init, __combine, __brick_reduce, __scan);
|
||||
auto __range = tbb::blocked_range<_Index>(0, __n);
|
||||
|
@ -1154,8 +1154,8 @@ __stable_sort_func<_RandomAccessIterator1, _RandomAccessIterator2, _Compare, _Le
|
|||
|
||||
template <class _ExecutionPolicy, typename _RandomAccessIterator, typename _Compare, typename _LeafSort>
|
||||
void
|
||||
__parallel_stable_sort(_ExecutionPolicy&&, _RandomAccessIterator __xs, _RandomAccessIterator __xe, _Compare __comp,
|
||||
_LeafSort __leaf_sort, std::size_t __nsort = 0)
|
||||
__parallel_stable_sort(__pstl::__internal::__tbb_backend_tag, _ExecutionPolicy&&, _RandomAccessIterator __xs,
|
||||
_RandomAccessIterator __xe, _Compare __comp, _LeafSort __leaf_sort, std::size_t __nsort = 0)
|
||||
{
|
||||
tbb::this_task_arena::isolate([=, &__nsort]() {
|
||||
//sorting based on task tree and parallel merge
|
||||
|
@ -1248,9 +1248,9 @@ operator()(__task* __self)
|
|||
template <class _ExecutionPolicy, typename _RandomAccessIterator1, typename _RandomAccessIterator2,
|
||||
typename _RandomAccessIterator3, typename _Compare, typename _LeafMerge>
|
||||
void
|
||||
__parallel_merge(_ExecutionPolicy&&, _RandomAccessIterator1 __xs, _RandomAccessIterator1 __xe,
|
||||
_RandomAccessIterator2 __ys, _RandomAccessIterator2 __ye, _RandomAccessIterator3 __zs, _Compare __comp,
|
||||
_LeafMerge __leaf_merge)
|
||||
__parallel_merge(__pstl::__internal::__tbb_backend_tag, _ExecutionPolicy&&, _RandomAccessIterator1 __xs,
|
||||
_RandomAccessIterator1 __xe, _RandomAccessIterator2 __ys, _RandomAccessIterator2 __ye,
|
||||
_RandomAccessIterator3 __zs, _Compare __comp, _LeafMerge __leaf_merge)
|
||||
{
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator1>::difference_type _DifferenceType1;
|
||||
typedef typename std::iterator_traits<_RandomAccessIterator2>::difference_type _DifferenceType2;
|
||||
|
@ -1279,7 +1279,7 @@ __parallel_merge(_ExecutionPolicy&&, _RandomAccessIterator1 __xs, _RandomAccessI
|
|||
//------------------------------------------------------------------------
|
||||
template <class _ExecutionPolicy, typename _F1, typename _F2>
|
||||
void
|
||||
__parallel_invoke(_ExecutionPolicy&&, _F1&& __f1, _F2&& __f2)
|
||||
__parallel_invoke(__pstl::__internal::__tbb_backend_tag, _ExecutionPolicy&&, _F1&& __f1, _F2&& __f2)
|
||||
{
|
||||
//TODO: a version of tbb::this_task_arena::isolate with variadic arguments pack should be added in the future
|
||||
tbb::this_task_arena::isolate([&]() { tbb::parallel_invoke(std::forward<_F1>(__f1), std::forward<_F2>(__f2)); });
|
||||
|
|
|
@ -24,17 +24,19 @@ namespace __internal
|
|||
//-----------------------------------------------------------------------
|
||||
/** Return extremum value returned by brick f[i,j) for subranges [i,j) of [first,last)
|
||||
Each f[i,j) must return a value in [i,j). */
|
||||
template <class _ExecutionPolicy, class _Index, class _Brick, class _Compare>
|
||||
template <class _BackendTag, class _ExecutionPolicy, class _Index, class _Brick, class _Compare>
|
||||
_Index
|
||||
__parallel_find(_ExecutionPolicy&& __exec, _Index __first, _Index __last, _Brick __f, _Compare __comp, bool __b_first)
|
||||
__parallel_find(_BackendTag __tag, _ExecutionPolicy&& __exec, _Index __first, _Index __last, _Brick __f,
|
||||
_Compare __comp, bool __b_first)
|
||||
{
|
||||
typedef typename std::iterator_traits<_Index>::difference_type _DifferenceType;
|
||||
const _DifferenceType __n = __last - __first;
|
||||
_DifferenceType __initial_dist = __b_first ? __n : -1;
|
||||
std::atomic<_DifferenceType> __extremum(__initial_dist);
|
||||
// TODO: find out what is better here: parallel_for or parallel_reduce
|
||||
__par_backend::__parallel_for(std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[__comp, __f, __first, &__extremum](_Index __i, _Index __j) {
|
||||
__par_backend::__parallel_for(__tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[__comp, __f, __first, &__extremum](_Index __i, _Index __j)
|
||||
{
|
||||
// See "Reducing Contention Through Priority Updates", PPoPP '13, for discussion of
|
||||
// why using a shared variable scales fairly well in this situation.
|
||||
if (__comp(__i - __first, __extremum))
|
||||
|
@ -59,13 +61,14 @@ __parallel_find(_ExecutionPolicy&& __exec, _Index __first, _Index __last, _Brick
|
|||
// parallel_or
|
||||
//------------------------------------------------------------------------
|
||||
//! Return true if brick f[i,j) returns true for some subrange [i,j) of [first,last)
|
||||
template <class _ExecutionPolicy, class _Index, class _Brick>
|
||||
template <class _BackendTag, class _ExecutionPolicy, class _Index, class _Brick>
|
||||
bool
|
||||
__parallel_or(_ExecutionPolicy&& __exec, _Index __first, _Index __last, _Brick __f)
|
||||
__parallel_or(_BackendTag __tag, _ExecutionPolicy&& __exec, _Index __first, _Index __last, _Brick __f)
|
||||
{
|
||||
std::atomic<bool> __found(false);
|
||||
__par_backend::__parallel_for(std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[__f, &__found](_Index __i, _Index __j) {
|
||||
__par_backend::__parallel_for(__tag, std::forward<_ExecutionPolicy>(__exec), __first, __last,
|
||||
[__f, &__found](_Index __i, _Index __j)
|
||||
{
|
||||
if (!__found.load(std::memory_order_relaxed) && __f(__i, __j))
|
||||
{
|
||||
__found.store(true, std::memory_order_relaxed);
|
||||
|
|
|
@ -11,12 +11,12 @@
|
|||
#define _PSTL_CONFIG_H
|
||||
|
||||
// The version is XYYZ, where X is major, YY is minor, and Z is patch (i.e. X.YY.Z)
|
||||
#define _PSTL_VERSION 12000
|
||||
#define _PSTL_VERSION 17000
|
||||
#define _PSTL_VERSION_MAJOR (_PSTL_VERSION / 1000)
|
||||
#define _PSTL_VERSION_MINOR ((_PSTL_VERSION % 1000) / 10)
|
||||
#define _PSTL_VERSION_PATCH (_PSTL_VERSION % 10)
|
||||
|
||||
#if !defined(_PSTL_PAR_BACKEND_SERIAL) && !defined(_PSTL_PAR_BACKEND_TBB)
|
||||
#if !defined(_PSTL_PAR_BACKEND_SERIAL) && !defined(_PSTL_PAR_BACKEND_TBB) && !defined(_PSTL_PAR_BACKEND_OPENMP)
|
||||
# error "A parallel backend must be specified"
|
||||
#endif
|
||||
|
||||
|
@ -53,13 +53,15 @@
|
|||
// the actual GCC version on the system.
|
||||
#define _PSTL_GCC_VERSION (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__)
|
||||
|
||||
#if __clang__
|
||||
#if defined(__clang__)
|
||||
// according to clang documentation, version can be vendor specific
|
||||
# define _PSTL_CLANG_VERSION (__clang_major__ * 10000 + __clang_minor__ * 100 + __clang_patchlevel__)
|
||||
#endif
|
||||
|
||||
// Enable SIMD for compilers that support OpenMP 4.0
|
||||
#if (_OPENMP >= 201307) || (__INTEL_COMPILER >= 1600) || (!defined(__INTEL_COMPILER) && _PSTL_GCC_VERSION >= 40900) || \
|
||||
#if (defined(_OPENMP) && _OPENMP >= 201307) || \
|
||||
(defined(__INTEL_COMPILER) && __INTEL_COMPILER >= 1600) || \
|
||||
(!defined(__INTEL_COMPILER) && _PSTL_GCC_VERSION >= 40900) || \
|
||||
defined(__clang__)
|
||||
# define _PSTL_PRAGMA_SIMD _PSTL_PRAGMA(omp simd)
|
||||
# define _PSTL_PRAGMA_DECLARE_SIMD _PSTL_PRAGMA(omp declare simd)
|
||||
|
@ -74,13 +76,13 @@
|
|||
# define _PSTL_PRAGMA_SIMD_REDUCTION(PRM)
|
||||
#endif //Enable SIMD
|
||||
|
||||
#if (__INTEL_COMPILER)
|
||||
#if defined(__INTEL_COMPILER)
|
||||
# define _PSTL_PRAGMA_FORCEINLINE _PSTL_PRAGMA(forceinline)
|
||||
#else
|
||||
# define _PSTL_PRAGMA_FORCEINLINE
|
||||
#endif
|
||||
|
||||
#if (__INTEL_COMPILER >= 1900)
|
||||
#if defined(__INTEL_COMPILER) && __INTEL_COMPILER >= 1900
|
||||
# define _PSTL_PRAGMA_SIMD_SCAN(PRM) _PSTL_PRAGMA(omp simd reduction(inscan, PRM))
|
||||
# define _PSTL_PRAGMA_SIMD_INCLUSIVE_SCAN(PRM) _PSTL_PRAGMA(omp scan inclusive(PRM))
|
||||
# define _PSTL_PRAGMA_SIMD_EXCLUSIVE_SCAN(PRM) _PSTL_PRAGMA(omp scan exclusive(PRM))
|
||||
|
@ -91,34 +93,50 @@
|
|||
#endif
|
||||
|
||||
// Should be defined to 1 for environments with a vendor implementation of C++17 execution policies
|
||||
#define _PSTL_CPP17_EXECUTION_POLICIES_PRESENT (_MSC_VER >= 1912)
|
||||
#define _PSTL_CPP17_EXECUTION_POLICIES_PRESENT (_MSC_VER >= 1912 && _MSVC_LANG >= 201703L) || \
|
||||
(_GLIBCXX_RELEASE >= 9 && __GLIBCXX__ >= 20190503 && __cplusplus >= 201703L)
|
||||
|
||||
#define _PSTL_CPP14_2RANGE_MISMATCH_EQUAL_PRESENT \
|
||||
(_MSC_VER >= 1900 || __cplusplus >= 201300L || __cpp_lib_robust_nonmodifying_seq_ops == 201304)
|
||||
#define _PSTL_CPP14_MAKE_REVERSE_ITERATOR_PRESENT \
|
||||
(_MSC_VER >= 1900 || __cplusplus >= 201402L || __cpp_lib_make_reverse_iterator == 201402)
|
||||
#define _PSTL_CPP14_INTEGER_SEQUENCE_PRESENT (_MSC_VER >= 1900 || __cplusplus >= 201402L)
|
||||
#define _PSTL_CPP14_VARIABLE_TEMPLATES_PRESENT \
|
||||
(!__INTEL_COMPILER || __INTEL_COMPILER >= 1700) && (_MSC_FULL_VER >= 190023918 || __cplusplus >= 201402L)
|
||||
|
||||
#define _PSTL_EARLYEXIT_PRESENT (__INTEL_COMPILER >= 1800)
|
||||
#define _PSTL_MONOTONIC_PRESENT (__INTEL_COMPILER >= 1800)
|
||||
|
||||
#if (__INTEL_COMPILER >= 1900 || !defined(__INTEL_COMPILER) && _PSTL_GCC_VERSION >= 40900 || _OPENMP >= 201307)
|
||||
# define _PSTL_UDR_PRESENT 1
|
||||
#else
|
||||
# define _PSTL_UDR_PRESENT 0
|
||||
#if (defined(_MSC_VER) && _MSC_VER >= 1900) || \
|
||||
__cplusplus >= 201300L || \
|
||||
__cpp_lib_robust_nonmodifying_seq_ops == 201304
|
||||
# define _PSTL_CPP14_2RANGE_MISMATCH_EQUAL_PRESENT
|
||||
#endif
|
||||
#if (defined(_MSC_VER) && _MSC_VER >= 1900) || \
|
||||
__cplusplus >= 201402L || \
|
||||
__cpp_lib_make_reverse_iterator == 201402
|
||||
# define _PSTL_CPP14_MAKE_REVERSE_ITERATOR_PRESENT
|
||||
#endif
|
||||
#if (defined(_MSC_VER) && _MSC_VER >= 1900) || __cplusplus >= 201402L
|
||||
# define _PSTL_CPP14_INTEGER_SEQUENCE_PRESENT
|
||||
#endif
|
||||
#if (defined(__INTEL_COMPILER) && __INTEL_COMPILER >= 1700) || \
|
||||
(defined(_MSC_FULL_VER) && _MSC_FULL_VER >= 190023918) || \
|
||||
__cplusplus >= 201402L
|
||||
# define _PSTL_CPP14_VARIABLE_TEMPLATES_PRESENT
|
||||
#endif
|
||||
|
||||
#define _PSTL_UDS_PRESENT (__INTEL_COMPILER >= 1900 && __INTEL_COMPILER_BUILD_DATE >= 20180626)
|
||||
#if defined(__INTEL_COMPILER) && __INTEL_COMPILER >= 1800
|
||||
# define _PSTL_EARLYEXIT_PRESENT
|
||||
# define _PSTL_MONOTONIC_PRESENT
|
||||
#endif
|
||||
|
||||
#if _PSTL_EARLYEXIT_PRESENT
|
||||
#if (defined(__INTEL_COMPILER) && __INTEL_COMPILER >= 1900) || \
|
||||
(!defined(__INTEL_COMPILER) && _PSTL_GCC_VERSION >= 40900) || \
|
||||
(defined(_OPENMP) && _OPENMP >= 201307)
|
||||
# define _PSTL_UDR_PRESENT
|
||||
#endif
|
||||
|
||||
#if defined(__INTEL_COMPILER) && __INTEL_COMPILER >= 1900 && __INTEL_COMPILER_BUILD_DATE >= 20180626
|
||||
# define _PSTL_UDS_PRESENT
|
||||
#endif
|
||||
|
||||
#if defined(_PSTL_EARLYEXIT_PRESENT)
|
||||
# define _PSTL_PRAGMA_SIMD_EARLYEXIT _PSTL_PRAGMA(omp simd early_exit)
|
||||
#else
|
||||
# define _PSTL_PRAGMA_SIMD_EARLYEXIT
|
||||
#endif
|
||||
|
||||
#if _PSTL_MONOTONIC_PRESENT
|
||||
#if defined(_PSTL_MONOTONIC_PRESENT)
|
||||
# define _PSTL_PRAGMA_SIMD_ORDERED_MONOTONIC(PRM) _PSTL_PRAGMA(omp ordered simd monotonic(PRM))
|
||||
# define _PSTL_PRAGMA_SIMD_ORDERED_MONOTONIC_2ARGS(PRM1, PRM2) _PSTL_PRAGMA(omp ordered simd monotonic(PRM1, PRM2))
|
||||
#else
|
||||
|
@ -136,7 +154,7 @@
|
|||
#define _PSTL_PRAGMA_DECLARE_REDUCTION(NAME, OP) \
|
||||
_PSTL_PRAGMA(omp declare reduction(NAME:OP : omp_out(omp_in)) initializer(omp_priv = omp_orig))
|
||||
|
||||
#if (__INTEL_COMPILER >= 1600)
|
||||
#if defined(__INTEL_COMPILER) && __INTEL_COMPILER >= 1600
|
||||
# define _PSTL_PRAGMA_VECTOR_UNALIGNED _PSTL_PRAGMA(vector unaligned)
|
||||
#else
|
||||
# define _PSTL_PRAGMA_VECTOR_UNALIGNED
|
||||
|
@ -149,7 +167,7 @@
|
|||
# define _PSTL_USE_NONTEMPORAL_STORES_IF_ALLOWED
|
||||
#endif
|
||||
|
||||
#if _MSC_VER || __INTEL_COMPILER //the preprocessors don't type a message location
|
||||
#if defined(_MSC_VER) || defined(__INTEL_COMPILER) // the preprocessors don't type a message location
|
||||
# define _PSTL_PRAGMA_LOCATION __FILE__ ":" _PSTL_STRING(__LINE__) ": [Parallel STL message]: "
|
||||
#else
|
||||
# define _PSTL_PRAGMA_LOCATION " [Parallel STL message]: "
|
||||
|
@ -157,7 +175,7 @@
|
|||
|
||||
#define _PSTL_PRAGMA_MESSAGE_IMPL(x) _PSTL_PRAGMA(message(_PSTL_STRING_CONCAT(_PSTL_PRAGMA_LOCATION, x)))
|
||||
|
||||
#if _PSTL_USAGE_WARNINGS
|
||||
#if defined(_PSTL_USAGE_WARNINGS)
|
||||
# define _PSTL_PRAGMA_MESSAGE(x) _PSTL_PRAGMA_MESSAGE_IMPL(x)
|
||||
# define _PSTL_PRAGMA_MESSAGE_POLICIES(x) _PSTL_PRAGMA_MESSAGE_IMPL(x)
|
||||
#else
|
||||
|
@ -166,8 +184,13 @@
|
|||
#endif
|
||||
|
||||
// broken macros
|
||||
#define _PSTL_CPP11_STD_ROTATE_BROKEN ((__GLIBCXX__ && __GLIBCXX__ < 20150716) || (_MSC_VER && _MSC_VER < 1800))
|
||||
#if (defined(__GLIBCXX__) && __GLIBCXX__ < 20150716) || \
|
||||
(defined(_MSC_VER) && _MSC_VER < 1800)
|
||||
# define _PSTL_CPP11_STD_ROTATE_BROKEN
|
||||
#endif
|
||||
|
||||
#define _PSTL_ICC_18_OMP_SIMD_BROKEN (__INTEL_COMPILER == 1800)
|
||||
#if defined(__INTEL_COMPILER) && __INTEL_COMPILER == 1800
|
||||
# define _PSTL_ICC_18_OMP_SIMD_BROKEN
|
||||
#endif
|
||||
|
||||
#endif /* _PSTL_CONFIG_H */
|
||||
|
|
|
@ -61,7 +61,7 @@ template <class _Index, class _DifferenceType, class _Pred>
|
|||
bool
|
||||
__simd_or(_Index __first, _DifferenceType __n, _Pred __pred) noexcept
|
||||
{
|
||||
#if _PSTL_EARLYEXIT_PRESENT
|
||||
#if defined(_PSTL_EARLYEXIT_PRESENT)
|
||||
_DifferenceType __i;
|
||||
_PSTL_PRAGMA_VECTOR_UNALIGNED
|
||||
_PSTL_PRAGMA_SIMD_EARLYEXIT
|
||||
|
@ -74,7 +74,7 @@ __simd_or(_Index __first, _DifferenceType __n, _Pred __pred) noexcept
|
|||
const _Index __last = __first + __n;
|
||||
while (__last != __first)
|
||||
{
|
||||
__INT32_TYPE__ __flag = 1;
|
||||
int32_t __flag = 1;
|
||||
_PSTL_PRAGMA_SIMD_REDUCTION(& : __flag)
|
||||
for (_DifferenceType __i = 0; __i < __block_size; ++__i)
|
||||
if (__pred(*(__first + __i)))
|
||||
|
@ -101,7 +101,7 @@ template <class _Index, class _DifferenceType, class _Compare>
|
|||
_Index
|
||||
__simd_first(_Index __first, _DifferenceType __begin, _DifferenceType __end, _Compare __comp) noexcept
|
||||
{
|
||||
#if _PSTL_EARLYEXIT_PRESENT
|
||||
#if defined(_PSTL_EARLYEXIT_PRESENT)
|
||||
_DifferenceType __i = __begin;
|
||||
_PSTL_PRAGMA_VECTOR_UNALIGNED // Do not generate peel loop part
|
||||
_PSTL_PRAGMA_SIMD_EARLYEXIT for (; __i < __end; ++__i)
|
||||
|
@ -161,7 +161,7 @@ template <class _Index1, class _DifferenceType, class _Index2, class _Pred>
|
|||
std::pair<_Index1, _Index2>
|
||||
__simd_first(_Index1 __first1, _DifferenceType __n, _Index2 __first2, _Pred __pred) noexcept
|
||||
{
|
||||
#if _PSTL_EARLYEXIT_PRESENT
|
||||
#if defined(_PSTL_EARLYEXIT_PRESENT)
|
||||
_DifferenceType __i = 0;
|
||||
_PSTL_PRAGMA_VECTOR_UNALIGNED
|
||||
_PSTL_PRAGMA_SIMD_EARLYEXIT
|
||||
|
@ -383,7 +383,7 @@ __simd_adjacent_find(_Index __first, _Index __last, _BinaryPredicate __pred, boo
|
|||
typedef typename std::iterator_traits<_Index>::difference_type _DifferenceType;
|
||||
_DifferenceType __i = 0;
|
||||
|
||||
#if _PSTL_EARLYEXIT_PRESENT
|
||||
#if defined(_PSTL_EARLYEXIT_PRESENT)
|
||||
//Some compiler versions fail to compile the following loop when iterators are used. Indices are used instead
|
||||
const _DifferenceType __n = __last - __first - 1;
|
||||
_PSTL_PRAGMA_VECTOR_UNALIGNED
|
||||
|
@ -532,7 +532,7 @@ struct _Combiner
|
|||
_BinaryOp* __bin_op; // Here is a pointer to function because of default ctor
|
||||
|
||||
_Combiner() : __value{}, __bin_op(nullptr) {}
|
||||
_Combiner(const _Tp& value, const _BinaryOp* __bin_op) : __value(value), __bin_op(const_cast<_BinaryOp*>(__bin_op)) {}
|
||||
_Combiner(const _Tp& __v, const _BinaryOp* __b) : __value(__v), __bin_op(const_cast<_BinaryOp*>(__b)) {}
|
||||
_Combiner(const _Combiner& __obj) : __value{}, __bin_op(__obj.__bin_op) {}
|
||||
|
||||
void
|
||||
|
@ -624,8 +624,8 @@ __simd_min_element(_ForwardIterator __first, _Size __n, _Compare __comp) noexcep
|
|||
_Compare* __min_comp;
|
||||
|
||||
_ComplexType() : __min_val{}, __min_ind{}, __min_comp(nullptr) {}
|
||||
_ComplexType(const _ValueType& __val, const _Compare* comp)
|
||||
: __min_val(__val), __min_ind(0), __min_comp(const_cast<_Compare*>(comp))
|
||||
_ComplexType(const _ValueType& val, const _Compare* comp)
|
||||
: __min_val(val), __min_ind(0), __min_comp(const_cast<_Compare*>(comp))
|
||||
{
|
||||
}
|
||||
_ComplexType(const _ComplexType& __obj)
|
||||
|
@ -685,9 +685,9 @@ __simd_minmax_element(_ForwardIterator __first, _Size __n, _Compare __comp) noex
|
|||
_Compare* __minmax_comp;
|
||||
|
||||
_ComplexType() : __min_val{}, __max_val{}, __min_ind{}, __max_ind{}, __minmax_comp(nullptr) {}
|
||||
_ComplexType(const _ValueType& __min_val, const _ValueType& __max_val, const _Compare* comp)
|
||||
: __min_val(__min_val), __max_val(__max_val), __min_ind(0), __max_ind(0),
|
||||
__minmax_comp(const_cast<_Compare*>(comp))
|
||||
_ComplexType(const _ValueType& __min, const _ValueType& __max, const _Compare* __comp)
|
||||
: __min_val(__min), __max_val(__max), __min_ind(0), __max_ind(0),
|
||||
__minmax_comp(const_cast<_Compare*>(__comp))
|
||||
{
|
||||
}
|
||||
_ComplexType(const _ComplexType& __obj)
|
||||
|
|
|
@ -19,8 +19,8 @@ namespace __internal
|
|||
{
|
||||
|
||||
template <typename _Fp>
|
||||
typename std::result_of<_Fp()>::type
|
||||
__except_handler(_Fp __f)
|
||||
auto
|
||||
__except_handler(_Fp __f) -> decltype(__f())
|
||||
{
|
||||
try
|
||||
{
|
||||
|
@ -44,8 +44,7 @@ __invoke_if(std::true_type, _Fp __f)
|
|||
}
|
||||
|
||||
template <typename _Fp>
|
||||
void
|
||||
__invoke_if(std::false_type, _Fp __f)
|
||||
void __invoke_if(std::false_type, _Fp)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -57,21 +56,20 @@ __invoke_if_not(std::false_type, _Fp __f)
|
|||
}
|
||||
|
||||
template <typename _Fp>
|
||||
void
|
||||
__invoke_if_not(std::true_type, _Fp __f)
|
||||
void __invoke_if_not(std::true_type, _Fp)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename _F1, typename _F2>
|
||||
typename std::result_of<_F1()>::type
|
||||
__invoke_if_else(std::true_type, _F1 __f1, _F2 __f2)
|
||||
auto
|
||||
__invoke_if_else(std::true_type, _F1 __f1, _F2) -> decltype(__f1())
|
||||
{
|
||||
return __f1();
|
||||
}
|
||||
|
||||
template <typename _F1, typename _F2>
|
||||
typename std::result_of<_F2()>::type
|
||||
__invoke_if_else(std::false_type, _F1 __f1, _F2 __f2)
|
||||
auto
|
||||
__invoke_if_else(std::false_type, _F1, _F2 __f2) -> decltype(__f2())
|
||||
{
|
||||
return __f2();
|
||||
}
|
||||
|
@ -87,23 +85,6 @@ struct __no_op
|
|||
}
|
||||
};
|
||||
|
||||
//! Logical negation of a predicate
|
||||
template <typename _Pred>
|
||||
class __not_pred
|
||||
{
|
||||
_Pred _M_pred;
|
||||
|
||||
public:
|
||||
explicit __not_pred(_Pred __pred) : _M_pred(__pred) {}
|
||||
|
||||
template <typename... _Args>
|
||||
bool
|
||||
operator()(_Args&&... __args)
|
||||
{
|
||||
return !_M_pred(std::forward<_Args>(__args)...);
|
||||
}
|
||||
};
|
||||
|
||||
template <typename _Pred>
|
||||
class __reorder_pred
|
||||
{
|
||||
|
@ -120,36 +101,6 @@ class __reorder_pred
|
|||
}
|
||||
};
|
||||
|
||||
//! "==" comparison.
|
||||
/** Not called "equal" to avoid (possibly unfounded) concerns about accidental invocation via
|
||||
argument-dependent name lookup by code expecting to find the usual std::equal. */
|
||||
class __pstl_equal
|
||||
{
|
||||
public:
|
||||
explicit __pstl_equal() {}
|
||||
|
||||
template <typename _Xp, typename _Yp>
|
||||
bool
|
||||
operator()(_Xp&& __x, _Yp&& __y) const
|
||||
{
|
||||
return std::forward<_Xp>(__x) == std::forward<_Yp>(__y);
|
||||
}
|
||||
};
|
||||
|
||||
//! "<" comparison.
|
||||
class __pstl_less
|
||||
{
|
||||
public:
|
||||
explicit __pstl_less() {}
|
||||
|
||||
template <typename _Xp, typename _Yp>
|
||||
bool
|
||||
operator()(_Xp&& __x, _Yp&& __y) const
|
||||
{
|
||||
return std::forward<_Xp>(__x) < std::forward<_Yp>(__y);
|
||||
}
|
||||
};
|
||||
|
||||
//! Like a polymorphic lambda for pred(...,value)
|
||||
template <typename _Tp, typename _Predicate>
|
||||
class __equal_value_by_pred
|
||||
|
|
|
@ -112,12 +112,12 @@ test_uninit_construct_by_type()
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
// for user-defined types
|
||||
#if !_PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN
|
||||
#if !defined(_PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN)
|
||||
test_uninit_construct_by_type<Wrapper<int32_t>>();
|
||||
test_uninit_construct_by_type<Wrapper<std::vector<std::string>>>();
|
||||
#endif
|
||||
|
|
|
@ -81,16 +81,16 @@ struct test_uninitialized_copy_move
|
|||
std::destroy_n(exec, out_first, n);
|
||||
}
|
||||
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || _PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN)
|
||||
template <typename InputIterator, typename OutputIterator>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
operator()(__pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
size_t n, /*is_trivial<T>=*/std::true_type)
|
||||
{
|
||||
}
|
||||
template <typename InputIterator, typename OutputIterator>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
OutputIterator out_first, size_t n, /*is_trivial<T>=*/std::true_type)
|
||||
{
|
||||
}
|
||||
|
@ -101,8 +101,6 @@ struct test_uninitialized_copy_move
|
|||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first, size_t n,
|
||||
/*is_trivial<T>=*/std::true_type)
|
||||
{
|
||||
typedef typename std::iterator_traits<InputIterator>::value_type T;
|
||||
|
||||
std::uninitialized_copy(exec, first, last, out_first);
|
||||
EXPECT_TRUE(IsCheckValueCorrectness(first, out_first, n), "wrong uninitialized_copy");
|
||||
std::destroy_n(exec, out_first, n);
|
||||
|
@ -134,7 +132,7 @@ test_uninitialized_copy_move_by_type()
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
|
@ -143,8 +141,8 @@ main()
|
|||
test_uninitialized_copy_move_by_type<float64_t>();
|
||||
|
||||
// for user-defined types
|
||||
#if !_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN && !_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN && \
|
||||
!_PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN
|
||||
#if !defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) && !defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) && \
|
||||
!defined(_PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN)
|
||||
test_uninitialized_copy_move_by_type<Wrapper<int8_t>>();
|
||||
#endif
|
||||
|
||||
|
|
|
@ -87,7 +87,7 @@ test_uninitialized_fill_destroy_by_type()
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
// for trivial types
|
||||
|
|
|
@ -30,18 +30,18 @@ using namespace TestUtils;
|
|||
|
||||
struct test_one_policy
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN // dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) // dummy specialization by policy type, in case of broken configuration
|
||||
template <typename BiDirIt1, typename Size, typename Generator1, typename Generator2, typename Compare>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, BiDirIt1 first1, BiDirIt1 last1, BiDirIt1 first2, BiDirIt1 last2,
|
||||
operator()(__pstl::execution::unsequenced_policy, BiDirIt1 first1, BiDirIt1 last1, BiDirIt1 first2, BiDirIt1 last2,
|
||||
Size n, Size m, Generator1 generator1, Generator2 generator2, Compare comp)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename BiDirIt1, typename Size, typename Generator1, typename Generator2, typename Compare>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, BiDirIt1 first1, BiDirIt1 last1, BiDirIt1 first2,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, BiDirIt1 first1, BiDirIt1 last1, BiDirIt1 first2,
|
||||
BiDirIt1 last2, Size n, Size m, Generator1 generator1, Generator2 generator2, Compare comp)
|
||||
{
|
||||
}
|
||||
|
@ -54,8 +54,6 @@ struct test_one_policy
|
|||
operator()(Policy&& exec, BiDirIt1 first1, BiDirIt1 last1, BiDirIt1 first2, BiDirIt1 last2, Size n, Size m,
|
||||
Generator1 generator1, Generator2 generator2, Compare comp)
|
||||
{
|
||||
|
||||
using T = typename std::iterator_traits<BiDirIt1>::value_type;
|
||||
const BiDirIt1 mid1 = std::next(first1, m);
|
||||
fill_data(first1, mid1, generator1);
|
||||
fill_data(mid1, last1, generator2);
|
||||
|
@ -72,8 +70,7 @@ struct test_one_policy
|
|||
template <typename Policy, typename BiDirIt1, typename Size, typename Generator1, typename Generator2,
|
||||
typename Compare>
|
||||
typename std::enable_if<is_same_iterator_category<BiDirIt1, std::forward_iterator_tag>::value, void>::type
|
||||
operator()(Policy&& exec, BiDirIt1 first1, BiDirIt1 last1, BiDirIt1 first2, BiDirIt1 last2, Size n, Size m,
|
||||
Generator1 generator1, Generator2 generator2, Compare comp)
|
||||
operator()(Policy&&, BiDirIt1, BiDirIt1, BiDirIt1, BiDirIt1, Size, Size, Generator1, Generator2, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -146,7 +143,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test_by_type<float64_t>([](int32_t i) { return -2 * i; }, [](int32_t i) { return -(2 * i + 1); },
|
||||
|
@ -160,6 +157,13 @@ main()
|
|||
|
||||
test_algo_basic_single<int32_t>(run_for_rnd_bi<test_non_const<int32_t>>());
|
||||
|
||||
test_by_type<MemoryChecker>(
|
||||
[](std::size_t idx){ return MemoryChecker{std::int32_t(idx * 2)}; },
|
||||
[](std::size_t idx){ return MemoryChecker{std::int32_t(idx * 2 + 1)}; },
|
||||
[](const MemoryChecker& val1, const MemoryChecker& val2){ return val1.value() == val2.value(); });
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() < 0, "wrong effect from inplace_merge: number of ctors calls < num of dtors calls");
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() > 0, "wrong effect from inplace_merge: number of ctors calls > num of dtors calls");
|
||||
|
||||
std::cout << done() << std::endl;
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -23,6 +23,7 @@
|
|||
#else
|
||||
#include <execution>
|
||||
#include <algorithm>
|
||||
#include <functional>
|
||||
#endif // PSTL_STANDALONE_TESTS
|
||||
|
||||
#include "pstl/test_utils.h"
|
||||
|
@ -58,8 +59,7 @@ struct test_merge
|
|||
void
|
||||
operator()(Policy&& exec, std::reverse_iterator<InputIterator1> first1, std::reverse_iterator<InputIterator1> last1,
|
||||
std::reverse_iterator<InputIterator2> first2, std::reverse_iterator<InputIterator2> last2,
|
||||
std::reverse_iterator<OutputIterator> out_first, std::reverse_iterator<OutputIterator> out_last,
|
||||
Compare comp)
|
||||
std::reverse_iterator<OutputIterator> out_first, std::reverse_iterator<OutputIterator> out_last, Compare)
|
||||
{
|
||||
using namespace std;
|
||||
typedef typename std::iterator_traits<std::reverse_iterator<InputIterator1>>::value_type T;
|
||||
|
@ -106,13 +106,13 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test_merge_by_type<int32_t>([](size_t v) { return (v % 2 == 0 ? v : -v) * 3; }, [](size_t v) { return v * 2; });
|
||||
test_merge_by_type<float64_t>([](size_t v) { return float64_t(v); }, [](size_t v) { return float64_t(v - 100); });
|
||||
|
||||
#if !_PSTL_ICC_16_17_TEST_64_TIMEOUT
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_64_TIMEOUT)
|
||||
test_merge_by_type<Wrapper<int16_t>>([](size_t v) { return Wrapper<int16_t>(v % 100); },
|
||||
[](size_t v) { return Wrapper<int16_t>(v % 10); });
|
||||
#endif
|
||||
|
|
|
@ -29,7 +29,7 @@ using namespace TestUtils;
|
|||
|
||||
struct run_copy_if
|
||||
{
|
||||
#if _PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN // dummy specializations to skip testing in case of broken configuration
|
||||
#if defined(_PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN) // dummy specializations to skip testing in case of broken configuration
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size,
|
||||
typename Predicate, typename T>
|
||||
void
|
||||
|
@ -131,7 +131,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<float64_t>(-666.0, [](const float64_t& x) { return x * x <= 1024; },
|
||||
|
@ -140,12 +140,12 @@ main()
|
|||
test<int32_t>(-666, [](const int32_t& x) { return x != 42; },
|
||||
[](size_t j) { return ((j + 1) % 5 & 2) != 0 ? int32_t(j + 1) : 42; });
|
||||
|
||||
#if !_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN
|
||||
#if !defined(_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN)
|
||||
test<Number>(Number(42, OddTag()), IsMultiple(3, OddTag()), [](int32_t j) { return Number(j, OddTag()); });
|
||||
#endif
|
||||
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN
|
||||
test<int32_t>(-666, [](const int32_t& x) { return true; }, [](size_t j) { return j; }, false);
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN)
|
||||
test<int32_t>(-666, [](const int32_t&) { return true; }, [](size_t j) { return j; }, false);
|
||||
#endif
|
||||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd_fw<test_non_const>());
|
||||
|
|
|
@ -31,11 +31,11 @@ using namespace TestUtils;
|
|||
struct run_copy
|
||||
{
|
||||
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size, typename T>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
operator()(__pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size size,
|
||||
Size n, T trash)
|
||||
{
|
||||
|
@ -43,7 +43,7 @@ struct run_copy
|
|||
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size, typename T>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
OutputIterator out_first, OutputIterator out_last, OutputIterator2 expected_first,
|
||||
OutputIterator2 expected_last, Size size, Size n, T trash)
|
||||
{
|
||||
|
@ -54,8 +54,7 @@ struct run_copy
|
|||
typename T>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size size,
|
||||
Size n, T trash)
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2, Size size, Size n, T trash)
|
||||
{
|
||||
// Cleaning
|
||||
std::fill_n(expected_first, size, trash);
|
||||
|
@ -84,11 +83,11 @@ template <typename T>
|
|||
struct run_move
|
||||
{
|
||||
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
operator()(__pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size size,
|
||||
Size n, T trash)
|
||||
{
|
||||
|
@ -96,7 +95,7 @@ struct run_move
|
|||
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
OutputIterator out_first, OutputIterator out_last, OutputIterator2 expected_first,
|
||||
OutputIterator2 expected_last, Size size, Size n, T trash)
|
||||
{
|
||||
|
@ -106,8 +105,7 @@ struct run_move
|
|||
template <typename Policy, typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size size,
|
||||
Size n, T trash)
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2, Size size, Size, T trash)
|
||||
{
|
||||
// Cleaning
|
||||
std::fill_n(expected_first, size, trash);
|
||||
|
@ -127,11 +125,11 @@ template <typename T>
|
|||
struct run_move<Wrapper<T>>
|
||||
{
|
||||
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
operator()(__pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size size,
|
||||
Size n, Wrapper<T> trash)
|
||||
{
|
||||
|
@ -139,7 +137,7 @@ struct run_move<Wrapper<T>>
|
|||
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
OutputIterator out_first, OutputIterator out_last, OutputIterator2 expected_first,
|
||||
OutputIterator2 expected_last, Size size, Size n, Wrapper<T> trash)
|
||||
{
|
||||
|
@ -149,8 +147,7 @@ struct run_move<Wrapper<T>>
|
|||
template <typename Policy, typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size size,
|
||||
Size n, Wrapper<T> trash)
|
||||
OutputIterator out_last, OutputIterator2, OutputIterator2, Size size, Size, Wrapper<T> trash)
|
||||
{
|
||||
// Cleaning
|
||||
std::fill_n(out_first, size, trash);
|
||||
|
@ -194,13 +191,13 @@ test(T trash, Convert convert)
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>(-666, [](size_t j) { return int32_t(j); });
|
||||
test<Wrapper<float64_t>>(Wrapper<float64_t>(-666.0), [](int32_t j) { return Wrapper<float64_t>(j); });
|
||||
|
||||
#if !_PSTL_ICC_16_17_TEST_64_TIMEOUT
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_64_TIMEOUT)
|
||||
test<float64_t>(-666.0, [](size_t j) { return float64_t(j); });
|
||||
test<Number>(Number(42, OddTag()), [](int32_t j) { return Number(j, OddTag()); });
|
||||
#endif
|
||||
|
|
|
@ -84,14 +84,14 @@ template <typename T>
|
|||
void
|
||||
test_fill_by_type(std::size_t n)
|
||||
{
|
||||
Sequence<T> in(n, [](std::size_t v) -> T { return T(0); }); //fill with zeros
|
||||
Sequence<T> in(n, [](std::size_t) -> T { return T(0); }); //fill with zeros
|
||||
T value = -1;
|
||||
|
||||
invoke_on_all_policies(test_fill(), in.begin(), in.end(), value);
|
||||
invoke_on_all_policies(test_fill_n(), in.begin(), n, value);
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
|
|
|
@ -57,17 +57,18 @@ struct test_generate
|
|||
{
|
||||
Generator_count<T> g;
|
||||
generate(exec, first, last, g);
|
||||
EXPECT_TRUE(std::count(first, last, g.default_value()) == n, "generate wrong result for generate");
|
||||
Size count = std::count(first, last, g.default_value());
|
||||
EXPECT_TRUE(count == n, "generate wrong result for generate");
|
||||
std::fill(first, last, T(0));
|
||||
}
|
||||
|
||||
{
|
||||
Generator_count<T> g;
|
||||
const auto m = n / 2;
|
||||
auto last = generate_n(exec, first, m, g);
|
||||
EXPECT_TRUE(std::count(first, last, g.default_value()) == m && last == std::next(first, m),
|
||||
"generate_n wrong result for generate_n");
|
||||
std::fill(first, last, T(0));
|
||||
auto actual_last = generate_n(exec, first, m, g);
|
||||
Size count = std::count(first, actual_last, g.default_value());
|
||||
EXPECT_TRUE(count == m && actual_last == std::next(first, m), "generate_n wrong result for generate_n");
|
||||
std::fill(first, actual_last, T(0));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
@ -78,7 +79,7 @@ test_generate_by_type()
|
|||
{
|
||||
for (size_t n = 0; n <= 100000; n = n < 16 ? n + 1 : size_t(3.1415 * n))
|
||||
{
|
||||
Sequence<T> in(n, [](size_t v) -> T { return T(0); }); //fill by zero
|
||||
Sequence<T> in(n, [](size_t) -> T { return T(0); }); //fill by zero
|
||||
|
||||
invoke_on_all_policies(test_generate(), in.begin(), in.end(), in.size());
|
||||
}
|
||||
|
@ -98,7 +99,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
|
|
|
@ -29,16 +29,16 @@ using namespace TestUtils;
|
|||
struct test_one_policy
|
||||
{
|
||||
//dummy specialization by policy type, in case of broken configuration
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || _PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN)
|
||||
|
||||
template <typename Iterator1, typename Predicate>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator1 begin1, Iterator1 end1, Predicate pred)
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator1 begin1, Iterator1 end1, Predicate pred)
|
||||
{
|
||||
}
|
||||
template <typename Iterator1, typename Predicate>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator1 begin1, Iterator1 end1, Predicate pred)
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator1 begin1, Iterator1 end1, Predicate pred)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
@ -92,14 +92,14 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<float64_t>([](const float64_t x) { return x < 0; });
|
||||
test<int32_t>([](const int32_t x) { return x > 1000; });
|
||||
test<uint16_t>([](const uint16_t x) { return x % 5 < 3; });
|
||||
#if !_PSTL_ICC_18_TEST_EARLY_EXIT_MONOTONIC_RELEASE_BROKEN && !_PSTL_ICC_19_TEST_IS_PARTITIONED_RELEASE_BROKEN
|
||||
test<LocalWrapper<float64_t>>([](const LocalWrapper<float64_t>& x) { return true; });
|
||||
#if !defined(_PSTL_ICC_18_TEST_EARLY_EXIT_MONOTONIC_RELEASE_BROKEN) && !defined(_PSTL_ICC_19_TEST_IS_PARTITIONED_RELEASE_BROKEN)
|
||||
test<LocalWrapper<float64_t>>([](const LocalWrapper<float64_t>&) { return true; });
|
||||
#endif
|
||||
|
||||
test_algo_basic_single<int32_t>(run_for_rnd_fw<test_non_const>());
|
||||
|
|
|
@ -66,15 +66,15 @@ is_equal(Iterator first, Iterator last, Iterator d_first)
|
|||
|
||||
template <typename Iterator>
|
||||
typename std::enable_if<!std::is_trivial<typename std::iterator_traits<Iterator>::value_type>::value, bool>::type
|
||||
is_equal(Iterator first, Iterator last, Iterator d_first)
|
||||
is_equal(Iterator, Iterator, Iterator)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
struct test_one_policy
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specializations to skip testing in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specializations to skip testing in case of broken configuration
|
||||
template <typename BiDirIt, typename Size, typename UnaryOp, typename Generator>
|
||||
void
|
||||
operator()(__pstl::execution::unsequenced_policy, BiDirIt first, BiDirIt last, BiDirIt exp_first, BiDirIt exp_last,
|
||||
|
@ -88,7 +88,7 @@ struct test_one_policy
|
|||
BiDirIt exp_last, Size n, UnaryOp unary_op, Generator generator)
|
||||
{
|
||||
}
|
||||
#elif _PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN //dummy specializations to skip testing in case of broken configuration
|
||||
#elif defined(_PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN) //dummy specializations to skip testing in case of broken configuration
|
||||
template <typename BiDirIt, typename Size, typename UnaryOp, typename Generator>
|
||||
void
|
||||
operator()(__pstl::execution::parallel_policy, BiDirIt first, BiDirIt last, BiDirIt exp_first, BiDirIt exp_last,
|
||||
|
@ -106,8 +106,8 @@ struct test_one_policy
|
|||
|
||||
template <typename Policy, typename BiDirIt, typename Size, typename UnaryOp, typename Generator>
|
||||
typename std::enable_if<!is_same_iterator_category<BiDirIt, std::forward_iterator_tag>::value, void>::type
|
||||
operator()(Policy&& exec, BiDirIt first, BiDirIt last, BiDirIt exp_first, BiDirIt exp_last, Size n,
|
||||
UnaryOp unary_op, Generator generator)
|
||||
operator()(Policy&& exec, BiDirIt first, BiDirIt last, BiDirIt exp_first, BiDirIt exp_last, Size, UnaryOp unary_op,
|
||||
Generator generator)
|
||||
{
|
||||
// partition
|
||||
{
|
||||
|
@ -130,8 +130,7 @@ struct test_one_policy
|
|||
}
|
||||
template <typename Policy, typename BiDirIt, typename Size, typename UnaryOp, typename Generator>
|
||||
typename std::enable_if<is_same_iterator_category<BiDirIt, std::forward_iterator_tag>::value, void>::type
|
||||
operator()(Policy&& exec, BiDirIt first, BiDirIt last, BiDirIt exp_first, BiDirIt exp_last, Size n,
|
||||
UnaryOp unary_op, Generator generator)
|
||||
operator()(Policy&&, BiDirIt, BiDirIt, BiDirIt, BiDirIt, Size, UnaryOp, Generator)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -170,10 +169,10 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN)
|
||||
test_by_type<int32_t>([](int32_t i) { return i; }, [](int32_t) { return true; });
|
||||
#endif
|
||||
test_by_type<float64_t>([](int32_t i) { return -i; }, [](const float64_t x) { return x < 0; });
|
||||
|
|
|
@ -35,24 +35,23 @@ struct test_partition_copy
|
|||
template <typename Policy, typename InputIterator, typename OutputIterator, typename OutputIterator2,
|
||||
typename UnaryOp>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator true_first,
|
||||
OutputIterator true_last, OutputIterator2 false_first, OutputIterator2 false_last, UnaryOp unary_op)
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator true_first, OutputIterator,
|
||||
OutputIterator2 false_first, OutputIterator2, UnaryOp unary_op)
|
||||
{
|
||||
|
||||
auto actual_ret = std::partition_copy(exec, first, last, true_first, false_first, unary_op);
|
||||
|
||||
EXPECT_TRUE(std::distance(true_first, actual_ret.first) == std::count_if(first, last, unary_op),
|
||||
"partition_copy has wrong effect from true sequence");
|
||||
EXPECT_TRUE(std::distance(false_first, actual_ret.second) ==
|
||||
std::count_if(first, last, __pstl::__internal::__not_pred<UnaryOp>(unary_op)),
|
||||
EXPECT_TRUE(std::distance(false_first, actual_ret.second) == std::count_if(first, last, std::not_fn(unary_op)),
|
||||
"partition_copy has wrong effect from false sequence");
|
||||
}
|
||||
|
||||
//dummy specialization by iterator type and policy type, in case of broken configuration
|
||||
#if _PSTL_ICC_1800_TEST_MONOTONIC_RELEASE_64_BROKEN
|
||||
#if defined(_PSTL_ICC_1800_TEST_MONOTONIC_RELEASE_64_BROKEN)
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename UnaryOp>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, std::reverse_iterator<InputIterator> first,
|
||||
operator()(__pstl::execution::unsequenced_policy, std::reverse_iterator<InputIterator> first,
|
||||
std::reverse_iterator<InputIterator> last, std::reverse_iterator<OutputIterator> true_first,
|
||||
std::reverse_iterator<OutputIterator> true_last, std::reverse_iterator<OutputIterator2> false_first,
|
||||
OutputIterator2 false_last, UnaryOp unary_op)
|
||||
|
@ -60,7 +59,7 @@ struct test_partition_copy
|
|||
}
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename UnaryOp>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, std::reverse_iterator<InputIterator> first,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, std::reverse_iterator<InputIterator> first,
|
||||
std::reverse_iterator<InputIterator> last, std::reverse_iterator<OutputIterator> true_first,
|
||||
std::reverse_iterator<OutputIterator> true_last, std::reverse_iterator<OutputIterator2> false_first,
|
||||
OutputIterator2 false_last, UnaryOp unary_op)
|
||||
|
@ -106,13 +105,13 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>([](const int32_t value) { return value % 2; });
|
||||
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN
|
||||
test<int32_t>([](const int32_t value) { return true; });
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN)
|
||||
test<int32_t>([](const int32_t) { return true; });
|
||||
#endif
|
||||
|
||||
test<float64_t>([](const float64_t value) { return value > 2 << 6; });
|
||||
|
|
|
@ -29,18 +29,18 @@ using namespace TestUtils;
|
|||
|
||||
struct run_remove
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename InputIterator, typename OutputIterator, typename Size, typename T>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
operator()(__pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator expected_first, OutputIterator expected_last, Size n,
|
||||
const T& value)
|
||||
{
|
||||
}
|
||||
template <typename InputIterator, typename OutputIterator, typename Size, typename T>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
OutputIterator out_first, OutputIterator out_last, OutputIterator expected_first,
|
||||
OutputIterator expected_last, Size n, const T& value)
|
||||
{
|
||||
|
@ -67,18 +67,18 @@ struct run_remove
|
|||
|
||||
struct run_remove_if
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename InputIterator, typename OutputIterator, typename Size, typename Predicate>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
operator()(__pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator expected_first, OutputIterator expected_last, Size n,
|
||||
Predicate pred)
|
||||
{
|
||||
}
|
||||
template <typename InputIterator, typename OutputIterator, typename Size, typename Predicate>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last,
|
||||
OutputIterator out_first, OutputIterator out_last, OutputIterator expected_first,
|
||||
OutputIterator expected_last, Size n, Predicate pred)
|
||||
{
|
||||
|
@ -138,11 +138,11 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
#if !_PSTL_ICC_18_TEST_EARLY_EXIT_MONOTONIC_RELEASE_BROKEN
|
||||
test<int32_t>(666, 42, [](int32_t val) { return true; }, [](size_t j) { return j; });
|
||||
#if !defined(_PSTL_ICC_18_TEST_EARLY_EXIT_MONOTONIC_RELEASE_BROKEN)
|
||||
test<int32_t>(666, 42, [](int32_t) { return true; }, [](size_t j) { return j; });
|
||||
#endif
|
||||
|
||||
test<int32_t>(666, 2001, [](const int32_t& val) { return val != 2001; },
|
||||
|
@ -150,13 +150,20 @@ main()
|
|||
test<float64_t>(-666.0, 8.5, [](const float64_t& val) { return val != 8.5; },
|
||||
[](size_t j) { return ((j + 1) % 7 & 2) != 0 ? 8.5 : float64_t(j % 32 + j); });
|
||||
|
||||
#if !_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN
|
||||
#if !defined(_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN)
|
||||
test<Number>(Number(-666, OddTag()), Number(42, OddTag()), IsMultiple(3, OddTag()),
|
||||
[](int32_t j) { return Number(j, OddTag()); });
|
||||
#endif
|
||||
|
||||
test_algo_basic_single<int32_t>(run_for_rnd_fw<test_non_const>());
|
||||
|
||||
test<MemoryChecker>(MemoryChecker{0}, MemoryChecker{1},
|
||||
[](const MemoryChecker& val){ return val.value() == 1; },
|
||||
[](std::size_t idx){ return MemoryChecker{std::int32_t(idx % 3 == 0)}; }
|
||||
);
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() < 0, "wrong effect from remove,remove_if: number of ctors calls < num of dtors calls");
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() > 0, "wrong effect from remove,remove_if: number of ctors calls > num of dtors calls");
|
||||
|
||||
std::cout << done() << std::endl;
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -33,16 +33,17 @@ struct run_remove_copy
|
|||
typename T>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size n,
|
||||
const T& value, T trash)
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2, Size n, const T& value,
|
||||
T trash)
|
||||
{
|
||||
// Cleaning
|
||||
std::fill_n(expected_first, n, trash);
|
||||
std::fill_n(out_first, n, trash);
|
||||
|
||||
// Run copy_if
|
||||
auto i = remove_copy(first, last, expected_first, value);
|
||||
auto k = remove_copy(exec, first, last, out_first, value);
|
||||
auto i = std::remove_copy(first, last, expected_first, value);
|
||||
(void)i;
|
||||
auto k = std::remove_copy(exec, first, last, out_first, value);
|
||||
EXPECT_EQ_N(expected_first, out_first, n, "wrong remove_copy effect");
|
||||
for (size_t j = 0; j < GuardSize; ++j)
|
||||
{
|
||||
|
@ -84,7 +85,7 @@ test(T trash, const T& value, Convert convert, bool check_weakness = true)
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
|
|
|
@ -31,9 +31,10 @@ struct copy_int
|
|||
{
|
||||
int32_t value;
|
||||
int32_t copied_times = 0;
|
||||
explicit copy_int(int32_t val = 0) { value = val; }
|
||||
constexpr explicit copy_int(int32_t val = 0) : value(val) {}
|
||||
constexpr copy_int(copy_int const& other) : value(other.value), copied_times(other.copied_times) { }
|
||||
|
||||
copy_int&
|
||||
constexpr copy_int&
|
||||
operator=(const copy_int& other)
|
||||
{
|
||||
if (&other == this)
|
||||
|
@ -46,7 +47,7 @@ struct copy_int
|
|||
return *this;
|
||||
}
|
||||
|
||||
bool
|
||||
constexpr bool
|
||||
operator==(const copy_int& other) const
|
||||
{
|
||||
return (value == other.value);
|
||||
|
@ -112,13 +113,13 @@ test(Pred pred)
|
|||
|
||||
const std::size_t max_len = 100000;
|
||||
|
||||
const T1 value = T1(0);
|
||||
const T1 new_value = T1(666);
|
||||
static constexpr T1 value = T1(0);
|
||||
static constexpr T1 new_value = T1(666);
|
||||
|
||||
Sequence<T2> expected(max_len);
|
||||
Sequence<T2> actual(max_len);
|
||||
|
||||
Sequence<T2> data(max_len, [&value](std::size_t i) {
|
||||
Sequence<T2> data(max_len, [](std::size_t i) {
|
||||
if (i % 3 == 2)
|
||||
{
|
||||
return T1(i);
|
||||
|
@ -153,7 +154,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t, float32_t>(__pstl::__internal::__equal_value<int32_t>(666));
|
||||
|
|
|
@ -34,8 +34,8 @@ struct test_replace_copy
|
|||
typename Predicate, typename T>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size n,
|
||||
Predicate pred, const T& old_value, const T& new_value, T trash)
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2, Size n, Predicate pred,
|
||||
const T& old_value, const T& new_value, T trash)
|
||||
{
|
||||
// Cleaning
|
||||
std::fill_n(expected_first, n, trash);
|
||||
|
@ -91,7 +91,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
|
@ -101,7 +101,7 @@ main()
|
|||
test<int32_t>(-666, 42, 99, [](const int32_t& x) { return x != 42; },
|
||||
[](size_t j) { return ((j + 1) % 5 & 2) != 0 ? 42 : -1 - int32_t(j); });
|
||||
|
||||
#if !_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN
|
||||
#if !defined(_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN)
|
||||
test<Number>(Number(42, OddTag()), Number(2001, OddTag()), Number(2017, OddTag()), IsMultiple(3, OddTag()),
|
||||
[](int32_t j) { return ((j + 1) % 3 & 2) != 0 ? Number(2001, OddTag()) : Number(j, OddTag()); });
|
||||
#endif
|
||||
|
|
|
@ -83,8 +83,8 @@ struct compare<wrapper<T>>
|
|||
struct test_one_policy
|
||||
{
|
||||
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN // dummy specializations to skip testing in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) // dummy specializations to skip testing in case of broken configuration
|
||||
template <typename Iterator, typename Size>
|
||||
void
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator data_b, Iterator data_e, Iterator actual_b,
|
||||
|
@ -123,10 +123,10 @@ struct test_one_policy
|
|||
template <typename ExecutionPolicy, typename Iterator, typename Size>
|
||||
typename std::enable_if<
|
||||
is_same_iterator_category<Iterator, std::random_access_iterator_tag>::value &&
|
||||
!std::is_same<ExecutionPolicy, __pstl::execution::sequenced_policy>::value &&
|
||||
!std::is_same<ExecutionPolicy, std::execution::sequenced_policy>::value &&
|
||||
std::is_same<typename std::iterator_traits<Iterator>::value_type, wrapper<float32_t>>::value,
|
||||
bool>::type
|
||||
check_move(ExecutionPolicy&& exec, Iterator b, Iterator e, Size shift)
|
||||
check_move(ExecutionPolicy&&, Iterator b, Iterator e, Size shift)
|
||||
{
|
||||
bool result = all_of(b, e, [](wrapper<float32_t>& a) {
|
||||
bool temp = a.move_count > 0;
|
||||
|
@ -139,10 +139,10 @@ struct test_one_policy
|
|||
template <typename ExecutionPolicy, typename Iterator, typename Size>
|
||||
typename std::enable_if<
|
||||
!(is_same_iterator_category<Iterator, std::random_access_iterator_tag>::value &&
|
||||
!std::is_same<ExecutionPolicy, __pstl::execution::sequenced_policy>::value &&
|
||||
!std::is_same<ExecutionPolicy, std::execution::sequenced_policy>::value &&
|
||||
std::is_same<typename std::iterator_traits<Iterator>::value_type, wrapper<float32_t>>::value),
|
||||
bool>::type
|
||||
check_move(ExecutionPolicy&& exec, Iterator b, Iterator e, Size shift)
|
||||
check_move(ExecutionPolicy&&, Iterator, Iterator, Size)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
@ -171,7 +171,7 @@ test()
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>();
|
||||
|
|
|
@ -78,17 +78,17 @@ struct comparator
|
|||
struct test_one_policy
|
||||
{
|
||||
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN // dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) // dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator1, typename Iterator2>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
Iterator2 actual_e, std::size_t shift)
|
||||
{
|
||||
}
|
||||
template <typename Iterator1, typename Iterator2>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
Iterator2 actual_e, std::size_t shift)
|
||||
{
|
||||
}
|
||||
|
@ -142,7 +142,7 @@ test()
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t, int8_t>();
|
||||
|
|
|
@ -61,7 +61,7 @@ template <typename T>
|
|||
struct check_swap
|
||||
{
|
||||
bool
|
||||
operator()(T& a)
|
||||
operator()(T&)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
@ -129,7 +129,7 @@ test()
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<wrapper<uint16_t>>();
|
||||
|
|
|
@ -70,10 +70,11 @@ struct test_one_policy
|
|||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename OutputIterator,
|
||||
typename BinaryOp>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2,
|
||||
OutputIterator out_first, OutputIterator out_last, BinaryOp op)
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2,
|
||||
OutputIterator out_first, OutputIterator, BinaryOp op)
|
||||
{
|
||||
auto orrr = std::transform(exec, first1, last1, first2, out_first, op);
|
||||
auto result = std::transform(exec, first1, last1, first2, out_first, op);
|
||||
(void)result;
|
||||
check_and_reset(first1, last1, first2, out_first);
|
||||
}
|
||||
};
|
||||
|
@ -87,7 +88,7 @@ test(Predicate pred)
|
|||
Sequence<In1> in1(n, [](size_t k) { return k % 5 != 1 ? 3 * k - 7 : 0; });
|
||||
Sequence<In2> in2(n, [](size_t k) { return k % 7 != 2 ? 5 * k - 5 : 0; });
|
||||
|
||||
Sequence<Out> out(n, [](size_t k) { return -1; });
|
||||
Sequence<Out> out(n, [](size_t) { return -1; });
|
||||
|
||||
invoke_on_all_policies(test_one_policy(), in1.begin(), in1.end(), in2.begin(), in2.end(), out.begin(),
|
||||
out.end(), pred);
|
||||
|
@ -110,7 +111,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
//const operator()
|
||||
|
|
|
@ -83,7 +83,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t, int32_t>();
|
||||
|
|
|
@ -29,32 +29,32 @@ using namespace TestUtils;
|
|||
|
||||
struct run_unique
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename ForwardIt, typename Generator>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, ForwardIt first1, ForwardIt last1, ForwardIt first2,
|
||||
operator()(__pstl::execution::unsequenced_policy, ForwardIt first1, ForwardIt last1, ForwardIt first2,
|
||||
ForwardIt last2, Generator generator)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename ForwardIt, typename Generator>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, ForwardIt first1, ForwardIt last1, ForwardIt first2,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, ForwardIt first1, ForwardIt last1, ForwardIt first2,
|
||||
ForwardIt last2, Generator generator)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename ForwardIt, typename BinaryPred, typename Generator>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, ForwardIt first1, ForwardIt last1, ForwardIt first2,
|
||||
operator()(__pstl::execution::unsequenced_policy, ForwardIt first1, ForwardIt last1, ForwardIt first2,
|
||||
ForwardIt last2, BinaryPred pred, Generator generator)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename ForwardIt, typename BinaryPred, typename Generator>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, ForwardIt first1, ForwardIt last1, ForwardIt first2,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, ForwardIt first1, ForwardIt last1, ForwardIt first2,
|
||||
ForwardIt last2, BinaryPred pred, Generator generator)
|
||||
{
|
||||
}
|
||||
|
@ -144,10 +144,10 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
#if !_PSTL_ICC_16_17_18_TEST_UNIQUE_MASK_RELEASE_BROKEN
|
||||
#if !defined(_PSTL_ICC_16_17_18_TEST_UNIQUE_MASK_RELEASE_BROKEN)
|
||||
test<int32_t>([](size_t j) { return j / 3; },
|
||||
[](const int32_t& val1, const int32_t& val2) { return val1 * val1 == val2 * val2; });
|
||||
test<float64_t>([](size_t) { return float64_t(1); },
|
||||
|
@ -160,6 +160,12 @@ main()
|
|||
|
||||
test_algo_basic_single<int32_t>(run_for_rnd_fw<test_non_const<int32_t>>());
|
||||
|
||||
test<MemoryChecker>(
|
||||
[](std::size_t idx){ return MemoryChecker{std::int32_t(idx / 3)}; },
|
||||
[](const MemoryChecker& val1, const MemoryChecker& val2){ return val1.value() == val2.value(); });
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() < 0, "wrong effect from unique: number of ctors calls < num of dtors calls");
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() > 0, "wrong effect from unique: number of ctors calls > num of dtors calls");
|
||||
|
||||
std::cout << done() << std::endl;
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -29,7 +29,7 @@ using namespace TestUtils;
|
|||
|
||||
struct run_unique_copy
|
||||
{
|
||||
#if _PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN // dummy specializations to skip testing in case of broken configuration
|
||||
#if defined(_PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN) // dummy specializations to skip testing in case of broken configuration
|
||||
template <typename InputIterator, typename OutputIterator, typename OutputIterator2, typename Size,
|
||||
typename Predicate, typename T>
|
||||
void
|
||||
|
@ -53,8 +53,8 @@ struct run_unique_copy
|
|||
typename Predicate, typename T>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2 expected_last, Size n,
|
||||
Predicate pred, T trash)
|
||||
OutputIterator out_last, OutputIterator2 expected_first, OutputIterator2, Size n, Predicate pred,
|
||||
T trash)
|
||||
{
|
||||
// Cleaning
|
||||
std::fill_n(expected_first, n, trash);
|
||||
|
@ -123,17 +123,17 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
main(int32_t argc, char* argv[])
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<Number>(Number(42, OddTag()), std::equal_to<Number>(),
|
||||
[](int32_t j) { return Number(3 * j / 13 ^ (j & 8), OddTag()); });
|
||||
|
||||
test<float32_t>(float32_t(42), std::equal_to<float32_t>(),
|
||||
[](int32_t j) { return float32_t(5 * j / 23 ^ (j / 7)); });
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN
|
||||
test<float32_t>(float32_t(42), [](float32_t x, float32_t y) { return false; },
|
||||
[](int32_t j) { return float32_t(j); }, false);
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN)
|
||||
test<float32_t>(float32_t(42), [](float32_t, float32_t) { return false; }, [](int32_t j) { return float32_t(j); },
|
||||
false);
|
||||
#endif
|
||||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd_fw<test_non_const<int32_t>>());
|
||||
|
|
|
@ -50,13 +50,13 @@ test_adjacent_find_by_type()
|
|||
{
|
||||
|
||||
size_t counts[] = {2, 3, 500};
|
||||
for (int32_t c = 0; c < const_size(counts); ++c)
|
||||
for (size_t c = 0; c < const_size(counts); ++c)
|
||||
{
|
||||
|
||||
for (int32_t e = 0; e < (counts[c] >= 64 ? 64 : (counts[c] == 2 ? 1 : 2)); ++e)
|
||||
for (size_t e = 0; e < (counts[c] >= 64 ? 64 : (counts[c] == 2 ? 1 : 2)); ++e)
|
||||
{
|
||||
Sequence<T> in(counts[c], [](int32_t v) -> T { return T(v); }); //fill 0...n
|
||||
in[e] = in[e + 1] = -1; //make an adjacent pair
|
||||
Sequence<T> in(counts[c], [](size_t v) -> T { return T(v); }); //fill 0...n
|
||||
in[e] = in[e + 1] = -1; //make an adjacent pair
|
||||
|
||||
auto i = std::adjacent_find(in.cbegin(), in.cend(), std::equal_to<T>());
|
||||
EXPECT_TRUE(i == in.cbegin() + e, "std::adjacent_find returned wrong result");
|
||||
|
@ -67,9 +67,9 @@ test_adjacent_find_by_type()
|
|||
}
|
||||
|
||||
//special cases: size=0, size=1;
|
||||
for (int32_t expect = 0; expect < 1; ++expect)
|
||||
for (size_t expect = 0; expect < 1; ++expect)
|
||||
{
|
||||
Sequence<T> in(expect, [](int32_t v) -> T { return T(v); }); //fill 0...n
|
||||
Sequence<T> in(expect, [](size_t v) -> T { return T(v); }); //fill 0...n
|
||||
auto i = std::adjacent_find(in.cbegin(), in.cend(), std::equal_to<T>());
|
||||
EXPECT_TRUE(i == in.cbegin() + expect, "std::adjacent_find returned wrong result");
|
||||
|
||||
|
@ -109,7 +109,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
|
|
|
@ -69,7 +69,7 @@ test(size_t bits)
|
|||
{
|
||||
|
||||
// Sequence of odd values
|
||||
Sequence<T> in(n, [n, bits](size_t k) { return T(2 * HashBits(n, bits - 1) ^ 1); });
|
||||
Sequence<T> in(n, [n, bits](size_t) { return T(2 * HashBits(n, bits - 1) ^ 1); });
|
||||
|
||||
// Even value, or false when T is bool.
|
||||
T spike(2 * HashBits(n, bits - 1));
|
||||
|
@ -108,13 +108,13 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>(8 * sizeof(int32_t));
|
||||
test<uint16_t>(8 * sizeof(uint16_t));
|
||||
test<float64_t>(53);
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN)
|
||||
test<bool>(1);
|
||||
#endif
|
||||
|
||||
|
|
|
@ -55,7 +55,7 @@ test(size_t bits)
|
|||
{
|
||||
|
||||
// Sequence of odd values
|
||||
Sequence<T> in(n, [n, bits](size_t k) { return T(2 * HashBits(n, bits - 1) ^ 1); });
|
||||
Sequence<T> in(n, [n, bits](size_t) { return T(2 * HashBits(n, bits - 1) ^ 1); });
|
||||
|
||||
// Even value, or false when T is bool.
|
||||
T spike(2 * HashBits(n, bits - 1));
|
||||
|
@ -94,13 +94,13 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>(8 * sizeof(int32_t));
|
||||
test<uint16_t>(8 * sizeof(uint16_t));
|
||||
test<float64_t>(53);
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN)
|
||||
test<bool>(1);
|
||||
#endif
|
||||
|
||||
|
|
|
@ -98,12 +98,12 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>(42, IsEqual<int32_t>(50, OddTag()), [](int32_t j) { return j; });
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN
|
||||
test<int32_t>(42, [](const int32_t& x) { return true; }, [](int32_t j) { return j; });
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_RELEASE_BROKEN)
|
||||
test<int32_t>(42, [](const int32_t&) { return true; }, [](int32_t j) { return j; });
|
||||
#endif
|
||||
test<float64_t>(42, IsEqual<float64_t>(50, OddTag()), [](int32_t j) { return float64_t(j); });
|
||||
test<Number>(Number(42, OddTag()), IsEqual<Number>(Number(50, OddTag()), OddTag()),
|
||||
|
|
|
@ -30,10 +30,10 @@ using namespace TestUtils;
|
|||
|
||||
struct UserType
|
||||
{
|
||||
size_t key;
|
||||
float32_t f;
|
||||
float64_t d;
|
||||
int32_t i;
|
||||
size_t key;
|
||||
|
||||
bool
|
||||
operator()(UserType a, UserType b)
|
||||
|
@ -157,14 +157,14 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
test<int32_t>(8 * sizeof(int32_t));
|
||||
test<uint16_t>(8 * sizeof(uint16_t));
|
||||
test<float64_t>(53);
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN)
|
||||
test<bool>(1);
|
||||
#endif
|
||||
test<UserType>(256);
|
||||
|
|
|
@ -29,16 +29,16 @@ using namespace TestUtils;
|
|||
|
||||
struct test_find
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator, typename Value>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator first, Iterator last, Value value)
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator first, Iterator last, Value value)
|
||||
{
|
||||
}
|
||||
template <typename Iterator, typename Value>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator first, Iterator last, Value value)
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator first, Iterator last, Value value)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
@ -88,12 +88,12 @@ class Weird
|
|||
Weird(int32_t val, OddTag) : value(val, OddTag()) {}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
// Note that the "hit" and "miss" functions here avoid overflow issues.
|
||||
test<Number>(Weird(42, OddTag()), [](int32_t j) { return Number(42, OddTag()); }, // hit
|
||||
[](int32_t j) { return Number(j == 42 ? 0 : j, OddTag()); }); // miss
|
||||
test<Number>(Weird(42, OddTag()), [](int32_t) { return Number(42, OddTag()); }, // hit
|
||||
[](int32_t j) { return Number(j == 42 ? 0 : j, OddTag()); }); // miss
|
||||
|
||||
// Test with value that is equal to two different bit patterns (-0.0 and 0.0)
|
||||
test<float32_t>(-0.0, [](int32_t j) { return j & 1 ? 0.0 : -0.0; }, // hit
|
||||
|
|
|
@ -26,105 +26,77 @@
|
|||
|
||||
using namespace TestUtils;
|
||||
|
||||
struct test_one_policy
|
||||
struct test_find
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator1, typename Iterator2, typename Predicate>
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator, typename Value>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator1 b, Iterator1 e, Iterator2 bsub, Iterator2 esub,
|
||||
Predicate pred)
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator first, Iterator last, Value value)
|
||||
{
|
||||
}
|
||||
template <typename Iterator1, typename Iterator2, typename Predicate>
|
||||
template <typename Iterator, typename Value>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator1 b, Iterator1 e, Iterator2 bsub, Iterator2 esub,
|
||||
Predicate pred)
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator first, Iterator last, Value value)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
||||
template <typename ExecutionPolicy, typename Iterator1, typename Iterator2, typename Predicate>
|
||||
template <typename Policy, typename Iterator, typename Value>
|
||||
void
|
||||
operator()(ExecutionPolicy&& exec, Iterator1 b, Iterator1 e, Iterator2 bsub, Iterator2 esub, Predicate pred)
|
||||
operator()(Policy&& exec, Iterator first, Iterator last, Value value)
|
||||
{
|
||||
using namespace std;
|
||||
// For find_end
|
||||
{
|
||||
auto expected = find_end(b, e, bsub, esub, pred);
|
||||
auto actual = find_end(exec, b, e, bsub, esub);
|
||||
EXPECT_TRUE(actual == expected, "wrong return result from find_end");
|
||||
|
||||
actual = find_end(exec, b, e, bsub, esub, pred);
|
||||
EXPECT_TRUE(actual == expected, "wrong return result from find_end with a predicate");
|
||||
}
|
||||
|
||||
// For search
|
||||
{
|
||||
auto expected = search(b, e, bsub, esub, pred);
|
||||
auto actual = search(exec, b, e, bsub, esub);
|
||||
EXPECT_TRUE(actual == expected, "wrong return result from search");
|
||||
|
||||
actual = search(exec, b, e, bsub, esub, pred);
|
||||
EXPECT_TRUE(actual == expected, "wrong return result from search with a predicate");
|
||||
}
|
||||
auto i = std::find(first, last, value);
|
||||
auto j = find(exec, first, last, value);
|
||||
EXPECT_TRUE(i == j, "wrong return value from find");
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
template <typename T, typename Value, typename Hit, typename Miss>
|
||||
void
|
||||
test(const std::size_t bits)
|
||||
test(Value value, Hit hit, Miss miss)
|
||||
{
|
||||
|
||||
const std::size_t max_n1 = 1000;
|
||||
const std::size_t max_n2 = (max_n1 * 10) / 8;
|
||||
Sequence<T> in(max_n1, [max_n1, bits](std::size_t) { return T(2 * HashBits(max_n1, bits - 1) ^ 1); });
|
||||
Sequence<T> sub(max_n2, [max_n1, bits](std::size_t) { return T(2 * HashBits(max_n1, bits - 1)); });
|
||||
for (std::size_t n1 = 0; n1 <= max_n1; n1 = n1 <= 16 ? n1 + 1 : size_t(3.1415 * n1))
|
||||
// Try sequences of various lengths.
|
||||
for (size_t n = 0; n <= 100000; n = n <= 16 ? n + 1 : size_t(3.1415 * n))
|
||||
{
|
||||
std::size_t sub_n[] = {0, 1, 3, n1, (n1 * 10) / 8};
|
||||
std::size_t res[] = {0, 1, n1 / 2, n1};
|
||||
for (auto n2 : sub_n)
|
||||
Sequence<T> in(n, [&](size_t k) -> T { return miss(n ^ k); });
|
||||
// Try different find positions, including not found.
|
||||
// By going backwards, we can add extra matches that are *not* supposed to be found.
|
||||
// The decreasing exponential gives us O(n) total work for the loop since each find takes O(m) time.
|
||||
for (size_t m = n; m > 0; m *= 0.6)
|
||||
{
|
||||
for (auto r : res)
|
||||
{
|
||||
std::size_t i = r, isub = 0;
|
||||
for (; i < n1 && isub < n2; ++i, ++isub)
|
||||
in[i] = sub[isub];
|
||||
invoke_on_all_policies(test_one_policy(), in.begin(), in.begin() + n1, sub.begin(), sub.begin() + n2,
|
||||
std::equal_to<T>());
|
||||
invoke_on_all_policies(test_one_policy(), in.cbegin(), in.cbegin() + n1, sub.cbegin(),
|
||||
sub.cbegin() + n2, std::equal_to<T>());
|
||||
}
|
||||
if (m < n)
|
||||
in[m] = hit(n ^ m);
|
||||
invoke_on_all_policies(test_find(), in.begin(), in.end(), value);
|
||||
invoke_on_all_policies(test_find(), in.cbegin(), in.cend(), value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
struct test_non_const
|
||||
// Type defined for sake of checking that std::find works with asymmetric ==.
|
||||
class Weird
|
||||
{
|
||||
template <typename Policy, typename FirstIterator, typename SecondInterator>
|
||||
void
|
||||
operator()(Policy&& exec, FirstIterator first_iter, SecondInterator second_iter)
|
||||
Number value;
|
||||
|
||||
public:
|
||||
friend bool
|
||||
operator==(Number x, Weird y)
|
||||
{
|
||||
invoke_if(exec, [&]() {
|
||||
find_end(exec, first_iter, first_iter, second_iter, second_iter, non_const(std::equal_to<T>()));
|
||||
search(exec, first_iter, first_iter, second_iter, second_iter, non_const(std::equal_to<T>()));
|
||||
});
|
||||
return x == y.value;
|
||||
}
|
||||
Weird(int32_t val, OddTag) : value(val, OddTag()) {}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>(8 * sizeof(int32_t));
|
||||
test<uint16_t>(8 * sizeof(uint16_t));
|
||||
test<float64_t>(53);
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN
|
||||
test<bool>(1);
|
||||
#endif
|
||||
// Note that the "hit" and "miss" functions here avoid overflow issues.
|
||||
test<Number>(Weird(42, OddTag()), [](int32_t) { return Number(42, OddTag()); }, // hit
|
||||
[](int32_t j) { return Number(j == 42 ? 0 : j, OddTag()); }); // miss
|
||||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd_fw<test_non_const<int32_t>>());
|
||||
// Test with value that is equal to two different bit patterns (-0.0 and 0.0)
|
||||
test<float32_t>(-0.0, [](int32_t j) { return j & 1 ? 0.0 : -0.0; }, // hit
|
||||
[](int32_t j) { return j == 0 ? ~j : j; }); // miss
|
||||
|
||||
std::cout << done() << std::endl;
|
||||
return 0;
|
||||
|
|
|
@ -28,17 +28,17 @@ using namespace TestUtils;
|
|||
|
||||
struct test_one_policy
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator1, typename Iterator2, typename Predicate>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator1 b, Iterator1 e, Iterator2 bsub, Iterator2 esub,
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator1 b, Iterator1 e, Iterator2 bsub, Iterator2 esub,
|
||||
Predicate pred)
|
||||
{
|
||||
}
|
||||
template <typename Iterator1, typename Iterator2, typename Predicate>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator1 b, Iterator1 e, Iterator2 bsub, Iterator2 esub,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator1 b, Iterator1 e, Iterator2 bsub, Iterator2 esub,
|
||||
Predicate pred)
|
||||
{
|
||||
}
|
||||
|
@ -66,8 +66,8 @@ test(Predicate pred)
|
|||
|
||||
const std::size_t max_n1 = 1000;
|
||||
const std::size_t max_n2 = (max_n1 * 10) / 8;
|
||||
Sequence<T> in1(max_n1, [](std::size_t k) { return T(1); });
|
||||
Sequence<T> in2(max_n2, [](std::size_t k) { return T(0); });
|
||||
Sequence<T> in1(max_n1, [](std::size_t) { return T(1); });
|
||||
Sequence<T> in2(max_n2, [](std::size_t) { return T(0); });
|
||||
for (std::size_t n1 = 0; n1 <= max_n1; n1 = n1 <= 16 ? n1 + 1 : size_t(3.1415 * n1))
|
||||
{
|
||||
std::size_t sub_n[] = {0, 1, n1 / 3, n1, (n1 * 10) / 8};
|
||||
|
@ -106,7 +106,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>(std::equal_to<int32_t>());
|
||||
|
|
|
@ -29,17 +29,17 @@ using namespace TestUtils;
|
|||
|
||||
struct test_find_if
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator, typename Predicate, typename NotPredicate>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator first, Iterator last, Predicate pred,
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator first, Iterator last, Predicate pred,
|
||||
NotPredicate not_pred)
|
||||
{
|
||||
}
|
||||
template <typename Iterator, typename Predicate, typename NotPredicate>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator first, Iterator last, Predicate pred,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator first, Iterator last, Predicate pred,
|
||||
NotPredicate not_pred)
|
||||
{
|
||||
}
|
||||
|
@ -97,10 +97,10 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
#if !_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN
|
||||
#if !defined(_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN)
|
||||
// Note that the "hit" and "miss" functions here avoid overflow issues.
|
||||
test<Number>(IsMultiple(5, OddTag()), [](int32_t j) { return Number(j - j % 5, OddTag()); }, // hit
|
||||
[](int32_t j) { return Number(j % 5 == 0 ? j ^ 1 : j, OddTag()); }); // miss
|
||||
|
|
|
@ -62,7 +62,7 @@ struct test_one_policy
|
|||
EXPECT_EQ_N(expected_first, first, n, "wrong effect from for_each");
|
||||
|
||||
// Try for_each_n
|
||||
std::for_each_n(__pstl::execution::seq, expected_first, n, Flip<T>(1));
|
||||
std::for_each_n(std::execution::seq, expected_first, n, Flip<T>(1));
|
||||
for_each_n(exec, first, n, Flip<T>(1));
|
||||
EXPECT_EQ_N(expected_first, first, n, "wrong effect from for_each_n");
|
||||
}
|
||||
|
@ -96,7 +96,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>();
|
||||
|
|
|
@ -53,7 +53,7 @@ struct test_mismatch
|
|||
using namespace std;
|
||||
typedef typename iterator_traits<Iterator1>::value_type T;
|
||||
{
|
||||
const auto expected = mismatch(__pstl::execution::seq, first1, last1, first2, last2, std::equal_to<T>());
|
||||
const auto expected = mismatch(std::execution::seq, first1, last1, first2, last2, std::equal_to<T>());
|
||||
const auto res1 = mismatch(exec, first1, last1, first2, last2, std::equal_to<T>());
|
||||
EXPECT_TRUE(expected == res1, "wrong return result from mismatch");
|
||||
const auto res2 = mismatch(exec, first1, last1, first2, last2);
|
||||
|
@ -129,7 +129,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
|
|
|
@ -55,7 +55,7 @@ test(size_t bits)
|
|||
{
|
||||
|
||||
// Sequence of odd values
|
||||
Sequence<T> in(n, [n, bits](size_t k) { return T(2 * HashBits(n, bits - 1) ^ 1); });
|
||||
Sequence<T> in(n, [n, bits](size_t) { return T(2 * HashBits(n, bits - 1) ^ 1); });
|
||||
|
||||
// Even value, or false when T is bool.
|
||||
T spike(2 * HashBits(n, bits - 1));
|
||||
|
@ -92,13 +92,13 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>(8 * sizeof(int32_t));
|
||||
test<uint16_t>(8 * sizeof(uint16_t));
|
||||
test<float64_t>(53);
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN)
|
||||
test<bool>(1);
|
||||
#endif
|
||||
|
||||
|
|
|
@ -78,17 +78,17 @@ is_equal(const T& x, const T& y)
|
|||
|
||||
struct test_one_policy
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN // dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) // dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator1, typename Size, typename Generator1, typename Generator2, typename Compare>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator1 first1, Iterator1 last1, Iterator1 first2,
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator1 first1, Iterator1 last1, Iterator1 first2,
|
||||
Iterator1 last2, Size n, Size m, Generator1 generator1, Generator2 generator2, Compare comp)
|
||||
{
|
||||
}
|
||||
template <typename Iterator1, typename Size, typename Generator1, typename Generator2, typename Compare>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator1 first1, Iterator1 last1, Iterator1 first2,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator1 first1, Iterator1 last1, Iterator1 first2,
|
||||
Iterator1 last2, Size n, Size m, Generator1 generator1, Generator2 generator2, Compare comp)
|
||||
{
|
||||
}
|
||||
|
@ -123,8 +123,7 @@ struct test_one_policy
|
|||
template <typename Policy, typename Iterator1, typename Size, typename Generator1, typename Generator2,
|
||||
typename Compare>
|
||||
typename std::enable_if<!is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(Policy&& exec, Iterator1 first1, Iterator1 last1, Iterator1 first2, Iterator1 last2, Size n, Size m,
|
||||
Generator1 generator1, Generator2 generator2, Compare comp)
|
||||
operator()(Policy&&, Iterator1, Iterator1, Iterator1, Iterator1, Size, Size, Generator1, Generator2, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -166,7 +165,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test_by_type<int32_t>([](int32_t i) { return 10 * i; }, [](int32_t i) { return i + 1; }, std::less<int32_t>());
|
||||
|
|
|
@ -30,17 +30,17 @@ using namespace TestUtils;
|
|||
|
||||
struct test_one_policy
|
||||
{
|
||||
#if _PSTL_ICC_18_VC141_TEST_SIMD_LAMBDA_RELEASE_BROKEN || _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN // dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_18_VC141_TEST_SIMD_LAMBDA_RELEASE_BROKEN) || defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) // dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator1, typename Iterator2>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
Iterator2 actual_e)
|
||||
{
|
||||
}
|
||||
template <typename Iterator1, typename Iterator2>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
Iterator2 actual_e)
|
||||
{
|
||||
}
|
||||
|
@ -63,7 +63,7 @@ struct test_one_policy
|
|||
|
||||
template <typename ExecutionPolicy, typename Iterator1, typename Iterator2>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::forward_iterator_tag>::value>::type
|
||||
operator()(ExecutionPolicy&& exec, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b, Iterator2 actual_e)
|
||||
operator()(ExecutionPolicy&&, Iterator1, Iterator1, Iterator2, Iterator2)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -98,13 +98,13 @@ struct wrapper
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>();
|
||||
test<uint16_t>();
|
||||
test<float64_t>();
|
||||
#if !_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN
|
||||
#if !defined(_PSTL_ICC_17_TEST_MAC_RELEASE_32_BROKEN)
|
||||
test<wrapper<float64_t>>();
|
||||
#endif
|
||||
|
||||
|
|
|
@ -70,16 +70,16 @@ struct test_one_policy
|
|||
Iterator data_e;
|
||||
test_one_policy(Iterator b, Iterator e) : data_b(b), data_e(e) {}
|
||||
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN // dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) // dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator1>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator1 actual_b, Iterator1 actual_e)
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator1 actual_b, Iterator1 actual_e)
|
||||
{
|
||||
}
|
||||
template <typename Iterator1>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator1 actual_b, Iterator1 actual_e)
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator1 actual_b, Iterator1 actual_e)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
@ -90,7 +90,6 @@ struct test_one_policy
|
|||
{
|
||||
using namespace std;
|
||||
using T = typename iterator_traits<Iterator1>::value_type;
|
||||
using DifferenceType = typename iterator_traits<Iterator1>::difference_type;
|
||||
|
||||
fill(actual_b, actual_e, T(-123));
|
||||
Iterator1 actual_return = reverse_copy(exec, data_b, data_e, actual_b);
|
||||
|
@ -127,11 +126,9 @@ test()
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
// clang-3.8 fails to correctly auto vectorize the loop in some cases of different types of container's elements,
|
||||
// for example: int32_t and int8_t. This issue isn't detected for clang-3.9 and newer versions.
|
||||
test<int16_t, int8_t>();
|
||||
test<uint16_t, float32_t>();
|
||||
test<float64_t, int64_t>();
|
||||
|
|
|
@ -28,16 +28,16 @@ using namespace TestUtils;
|
|||
|
||||
struct test_one_policy
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator, typename Size, typename T, typename Predicate>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator b, Iterator e, Size count, const T& value, Predicate pred)
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator b, Iterator e, Size count, const T& value, Predicate pred)
|
||||
{
|
||||
}
|
||||
template <typename Iterator, typename Size, typename T, typename Predicate>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator b, Iterator e, Size count, const T& value,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator b, Iterator e, Size count, const T& value,
|
||||
Predicate pred)
|
||||
{
|
||||
}
|
||||
|
@ -77,7 +77,7 @@ test()
|
|||
}
|
||||
for (auto r : res)
|
||||
{
|
||||
Sequence<T> in(n1, [n1](std::size_t k) { return T(0); });
|
||||
Sequence<T> in(n1, [](std::size_t) { return T(0); });
|
||||
std::size_t i = r, isub = 0;
|
||||
for (; i < n1 && isub < n2; ++i, ++isub)
|
||||
in[i] = value;
|
||||
|
@ -100,13 +100,13 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<int32_t>();
|
||||
test<uint16_t>();
|
||||
test<float64_t>();
|
||||
#if !_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN
|
||||
#if !defined(_PSTL_ICC_16_17_TEST_REDUCTION_BOOL_TYPE_RELEASE_64_BROKEN)
|
||||
test<bool>();
|
||||
#endif
|
||||
|
||||
|
|
|
@ -67,8 +67,7 @@ struct test_one_policy
|
|||
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2,
|
||||
Compare comp)
|
||||
operator()(Policy&&, InputIterator1, InputIterator1, InputIterator2, InputIterator2, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -104,11 +103,11 @@ test_includes(Compare compare)
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
test_includes<float64_t, float64_t>(__pstl::__internal::__pstl_less());
|
||||
test_includes<float64_t, float64_t>(std::less<>());
|
||||
test_includes<Num<int64_t>, Num<int32_t>>([](const Num<int64_t>& x, const Num<int32_t>& y) { return x < y; });
|
||||
std::cout << done() << std::endl;
|
||||
|
||||
|
|
|
@ -43,16 +43,16 @@ struct WithCmpOp
|
|||
|
||||
struct test_is_heap
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator, typename Predicate>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator first, Iterator last, Predicate pred)
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator first, Iterator last, Predicate pred)
|
||||
{
|
||||
}
|
||||
template <typename Iterator, typename Predicate>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator first, Iterator last, Predicate pred)
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator first, Iterator last, Predicate pred)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
@ -87,13 +87,14 @@ struct test_is_heap
|
|||
const Iterator actual = is_heap_until(exec, first, last, pred);
|
||||
const auto x = std::distance(first, actual);
|
||||
EXPECT_TRUE(expected == actual, "wrong return value from is_heap_until with predicate");
|
||||
EXPECT_EQ(x, y, "both iterators should be the same distance away from 'first'");
|
||||
}
|
||||
}
|
||||
|
||||
// is_heap, is_heap_until works only with random access iterators
|
||||
template <typename Policy, typename Iterator, typename Predicate>
|
||||
typename std::enable_if<!is_same_iterator_category<Iterator, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(Policy&& exec, Iterator first, Iterator last, Predicate pred)
|
||||
operator()(Policy&&, Iterator, Iterator, Predicate)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -121,7 +122,7 @@ test_is_heap_by_type(Comp comp)
|
|||
invoke_on_all_policies(test_is_heap(), in.cbegin(), in.cend(), comp);
|
||||
}
|
||||
|
||||
Sequence<T> in(max_size / 10, [](size_t v) -> T { return T(1); });
|
||||
Sequence<T> in(max_size / 10, [](size_t) -> T { return T(1); });
|
||||
invoke_on_all_policies(test_is_heap(), in.begin(), in.end(), comp);
|
||||
}
|
||||
|
||||
|
@ -139,7 +140,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test_is_heap_by_type<float32_t>(std::greater<float32_t>());
|
||||
|
|
|
@ -76,7 +76,7 @@ test_is_sorted_by_type()
|
|||
invoke_on_all_policies(test_is_sorted(), in0.cbegin(), in0.cend(), std::is_sorted(in0.begin(), in0.end()));
|
||||
|
||||
//non-descending order
|
||||
Sequence<T> in1(9, [](size_t v) -> T { return T(0); });
|
||||
Sequence<T> in1(9, [](size_t) -> T { return T(0); });
|
||||
invoke_on_all_policies(test_is_sorted(), in1.begin(), in1.end(), std::is_sorted(in1.begin(), in1.end()));
|
||||
invoke_on_all_policies(test_is_sorted(), in1.cbegin(), in1.cend(), std::is_sorted(in1.begin(), in1.end()));
|
||||
}
|
||||
|
@ -93,7 +93,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
|
|
|
@ -165,12 +165,12 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<uint16_t, float64_t>(std::less<float64_t>());
|
||||
test<float32_t, int32_t>(std::greater<float32_t>());
|
||||
#if !_PSTL_ICC_18_TEST_EARLY_EXIT_AVX_RELEASE_BROKEN
|
||||
#if !defined(_PSTL_ICC_18_TEST_EARLY_EXIT_AVX_RELEASE_BROKEN)
|
||||
test<float64_t, int32_t>([](const float64_t x, const int32_t y) { return x * x < y * y; });
|
||||
#endif
|
||||
test<LocalWrapper<int32_t>, LocalWrapper<int32_t>>(
|
||||
|
|
|
@ -184,7 +184,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
using TestUtils::float64_t;
|
||||
|
|
|
@ -90,19 +90,18 @@ struct test_brick_partial_sort
|
|||
//checking upper bound number of comparisons; O(p*(last-first)log(middle-first)); where p - number of threads;
|
||||
if (m1 - first > 1)
|
||||
{
|
||||
auto complex = std::ceil(n * std::log(float32_t(m1 - first)));
|
||||
#if _PSTL_USE_PAR_POLICIES
|
||||
auto p = tbb::this_task_arena::max_concurrency();
|
||||
#else
|
||||
auto p = 1;
|
||||
#endif
|
||||
|
||||
#ifdef _DEBUG
|
||||
# if defined(_PSTL_PAR_BACKEND_TBB)
|
||||
auto p = tbb::this_task_arena::max_concurrency();
|
||||
# else
|
||||
auto p = 1;
|
||||
# endif
|
||||
auto complex = std::ceil(n * std::log(float32_t(m1 - first)));
|
||||
if (count_comp > complex * p)
|
||||
{
|
||||
std::cout << "complexity exceeded" << std::endl;
|
||||
}
|
||||
#endif
|
||||
#endif // _DEBUG
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -110,8 +109,7 @@ struct test_brick_partial_sort
|
|||
template <typename Policy, typename InputIterator, typename Compare>
|
||||
typename std::enable_if<!is_same_iterator_category<InputIterator, std::random_access_iterator_tag>::value,
|
||||
void>::type
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, InputIterator exp_first, InputIterator exp_last,
|
||||
Compare compare)
|
||||
operator()(Policy&&, InputIterator, InputIterator, InputIterator, InputIterator, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -142,7 +140,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
count_val = 0;
|
||||
|
|
|
@ -64,32 +64,32 @@ struct test_one_policy
|
|||
: d_first(b1), d_last(e1), exp_first(b2), exp_last(e2)
|
||||
{
|
||||
}
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN // dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) // dummy specialization by policy type, in case of broken configuration
|
||||
template <typename InputIterator, typename Size, typename T, typename Compare>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, Size n1, Size n2,
|
||||
operator()(__pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, Size n1, Size n2,
|
||||
const T& trash, Compare compare)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename InputIterator, typename Size, typename T, typename Compare>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last, Size n1, Size n2,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last, Size n1, Size n2,
|
||||
const T& trash, Compare compare)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename InputIterator, typename Size, typename T>
|
||||
void
|
||||
operator()(pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, Size n1, Size n2,
|
||||
operator()(__pstl::execution::unsequenced_policy, InputIterator first, InputIterator last, Size n1, Size n2,
|
||||
const T& trash)
|
||||
{
|
||||
}
|
||||
|
||||
template <typename InputIterator, typename Size, typename T>
|
||||
void
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last, Size n1, Size n2,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, InputIterator first, InputIterator last, Size n1, Size n2,
|
||||
const T& trash)
|
||||
{
|
||||
}
|
||||
|
@ -187,7 +187,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test_partial_sort_copy<Num<float32_t>>([](Num<float32_t> x, Num<float32_t> y) { return x < y; });
|
||||
|
@ -195,6 +195,11 @@ main()
|
|||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd<test_non_const<int32_t>>());
|
||||
|
||||
test_partial_sort_copy<MemoryChecker>(
|
||||
[](const MemoryChecker& val1, const MemoryChecker& val2){ return val1.value() < val2.value(); });
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() < 0, "wrong effect from partial_sort_copy: number of ctors calls < num of dtors calls");
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() > 0, "wrong effect from partial_sort_copy: number of ctors calls > num of dtors calls");
|
||||
|
||||
std::cout << done() << std::endl;
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -60,7 +60,8 @@ struct Num
|
|||
}
|
||||
};
|
||||
|
||||
struct test_one_policy
|
||||
template <typename Type>
|
||||
struct test_set_union
|
||||
{
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<!TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
|
@ -75,30 +76,98 @@ struct test_one_policy
|
|||
Sequence<T1> expect(n);
|
||||
Sequence<T1> out(n);
|
||||
|
||||
//1. set_union
|
||||
auto expect_res = std::set_union(first1, last1, first2, last2, expect.begin(), comp);
|
||||
auto res = std::set_union(exec, first1, last1, first2, last2, out.begin(), comp);
|
||||
|
||||
EXPECT_TRUE(expect_res - expect.begin() == res - out.begin(), "wrong result for set_union");
|
||||
EXPECT_EQ_N(expect.begin(), out.begin(), std::distance(out.begin(), res), "wrong set_union effect");
|
||||
}
|
||||
|
||||
//2. set_intersection
|
||||
expect_res = std::set_intersection(first1, last1, first2, last2, expect.begin(), comp);
|
||||
res = std::set_intersection(exec, first1, last1, first2, last2, out.begin(), comp);
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
operator()(Policy&&, InputIterator1, InputIterator1, InputIterator2, InputIterator2, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Type>
|
||||
struct test_set_intersection
|
||||
{
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<!TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2,
|
||||
Compare comp)
|
||||
{
|
||||
using T1 = typename std::iterator_traits<InputIterator1>::value_type;
|
||||
|
||||
auto n1 = std::distance(first1, last1);
|
||||
auto n2 = std::distance(first2, last2);
|
||||
auto n = n1 + n2;
|
||||
Sequence<T1> expect(n);
|
||||
Sequence<T1> out(n);
|
||||
|
||||
auto expect_res = std::set_intersection(first1, last1, first2, last2, expect.begin(), comp);
|
||||
auto res = std::set_intersection(exec, first1, last1, first2, last2, out.begin(), comp);
|
||||
|
||||
EXPECT_TRUE(expect_res - expect.begin() == res - out.begin(), "wrong result for set_intersection");
|
||||
EXPECT_EQ_N(expect.begin(), out.begin(), std::distance(out.begin(), res), "wrong set_intersection effect");
|
||||
}
|
||||
|
||||
//3. set_difference
|
||||
expect_res = std::set_difference(first1, last1, first2, last2, expect.begin(), comp);
|
||||
res = std::set_difference(exec, first1, last1, first2, last2, out.begin(), comp);
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
operator()(Policy&&, InputIterator1, InputIterator1, InputIterator2, InputIterator2, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Type>
|
||||
struct test_set_difference
|
||||
{
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<!TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2,
|
||||
Compare comp)
|
||||
{
|
||||
using T1 = typename std::iterator_traits<InputIterator1>::value_type;
|
||||
|
||||
auto n1 = std::distance(first1, last1);
|
||||
auto n2 = std::distance(first2, last2);
|
||||
auto n = n1 + n2;
|
||||
Sequence<T1> expect(n);
|
||||
Sequence<T1> out(n);
|
||||
|
||||
auto expect_res = std::set_difference(first1, last1, first2, last2, expect.begin(), comp);
|
||||
auto res = std::set_difference(exec, first1, last1, first2, last2, out.begin(), comp);
|
||||
|
||||
EXPECT_TRUE(expect_res - expect.begin() == res - out.begin(), "wrong result for set_difference");
|
||||
EXPECT_EQ_N(expect.begin(), out.begin(), std::distance(out.begin(), res), "wrong set_difference effect");
|
||||
}
|
||||
|
||||
//4. set_symmetric_difference
|
||||
expect_res = std::set_symmetric_difference(first1, last1, first2, last2, expect.begin(), comp);
|
||||
res = std::set_symmetric_difference(exec, first1, last1, first2, last2, out.begin(), comp);
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
operator()(Policy&&, InputIterator1, InputIterator1, InputIterator2, InputIterator2, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
template <typename Type>
|
||||
struct test_set_symmetric_difference
|
||||
{
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<!TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2,
|
||||
Compare comp)
|
||||
{
|
||||
using T1 = typename std::iterator_traits<InputIterator1>::value_type;
|
||||
|
||||
auto n1 = std::distance(first1, last1);
|
||||
auto n2 = std::distance(first2, last2);
|
||||
auto n = n1 + n2;
|
||||
Sequence<T1> expect(n);
|
||||
Sequence<T1> out(n);
|
||||
|
||||
auto expect_res = std::set_symmetric_difference(first1, last1, first2, last2, expect.begin(), comp);
|
||||
auto res = std::set_symmetric_difference(exec, first1, last1, first2, last2, out.begin(), comp);
|
||||
|
||||
EXPECT_TRUE(expect_res - expect.begin() == res - out.begin(), "wrong result for set_symmetric_difference");
|
||||
EXPECT_EQ_N(expect.begin(), out.begin(), std::distance(out.begin(), res),
|
||||
|
@ -107,8 +176,7 @@ struct test_one_policy
|
|||
|
||||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename Compare>
|
||||
typename std::enable_if<TestUtils::isReverse<InputIterator1>::value, void>::type
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2,
|
||||
Compare comp)
|
||||
operator()(Policy&&, InputIterator1, InputIterator1, InputIterator2, InputIterator2, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -128,43 +196,92 @@ test_set(Compare compare)
|
|||
for (std::size_t m = 0; m < n_max; m = m <= 16 ? m + 1 : size_t(2.71828 * m))
|
||||
{
|
||||
//prepare the input ranges
|
||||
Sequence<T1> in1(n, [n](std::size_t k) { return rand() % (2 * k + 1); });
|
||||
Sequence<T1> in1(n, [](std::size_t k) { return rand() % (2 * k + 1); });
|
||||
Sequence<T2> in2(m, [m](std::size_t k) { return (m % 2) * rand() + rand() % (k + 1); });
|
||||
|
||||
std::sort(in1.begin(), in1.end(), compare);
|
||||
std::sort(in2.begin(), in2.end(), compare);
|
||||
|
||||
invoke_on_all_policies(test_one_policy(), in1.begin(), in1.end(), in2.cbegin(), in2.cend(), compare);
|
||||
invoke_on_all_policies(test_set_union<T1>(), in1.begin(), in1.end(), in2.cbegin(), in2.cend(),
|
||||
compare);
|
||||
|
||||
invoke_on_all_policies(test_set_intersection<T1>(), in1.begin(), in1.end(), in2.cbegin(), in2.cend(),
|
||||
compare);
|
||||
|
||||
invoke_on_all_policies(test_set_difference<T1>(), in1.begin(), in1.end(), in2.cbegin(), in2.cend(),
|
||||
compare);
|
||||
|
||||
invoke_on_all_policies(test_set_symmetric_difference<T1>(), in1.begin(), in1.end(), in2.cbegin(),
|
||||
in2.cend(), compare);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
struct test_non_const
|
||||
struct test_non_const_set_difference
|
||||
{
|
||||
template <typename Policy, typename InputIterator, typename OutputInterator>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator input_iter, OutputInterator out_iter)
|
||||
{
|
||||
set_difference(exec, input_iter, input_iter, input_iter, input_iter, out_iter, non_const(std::less<T>()));
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct test_non_const_set_intersection
|
||||
{
|
||||
template <typename Policy, typename InputIterator, typename OutputInterator>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator input_iter, OutputInterator out_iter)
|
||||
{
|
||||
set_intersection(exec, input_iter, input_iter, input_iter, input_iter, out_iter, non_const(std::less<T>()));
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct test_non_const_set_symmetric_difference
|
||||
{
|
||||
template <typename Policy, typename InputIterator, typename OutputInterator>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator input_iter, OutputInterator out_iter)
|
||||
{
|
||||
set_symmetric_difference(exec, input_iter, input_iter, input_iter, input_iter, out_iter,
|
||||
non_const(std::less<T>()));
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct test_non_const_set_union
|
||||
{
|
||||
template <typename Policy, typename InputIterator, typename OutputInterator>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator input_iter, OutputInterator out_iter)
|
||||
{
|
||||
set_union(exec, input_iter, input_iter, input_iter, input_iter, out_iter, non_const(std::less<T>()));
|
||||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
|
||||
test_set<float64_t, float64_t>(__pstl::__internal::__pstl_less());
|
||||
test_set<float64_t, float64_t>(std::less<>());
|
||||
test_set<Num<int64_t>, Num<int32_t>>([](const Num<int64_t>& x, const Num<int32_t>& y) { return x < y; });
|
||||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd_fw<test_non_const<int32_t>>());
|
||||
test_set<MemoryChecker, MemoryChecker>([](const MemoryChecker& val1, const MemoryChecker& val2) -> bool {
|
||||
return val1.value() < val2.value();
|
||||
});
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() < 0, "wrong effect from set algorithms: number of ctors calls < num of dtors calls");
|
||||
EXPECT_FALSE(MemoryChecker::alive_objects() > 0, "wrong effect from set algorithms: number of ctors calls > num of dtors calls");
|
||||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd_fw<test_non_const_set_difference<int32_t>>());
|
||||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd_fw<test_non_const_set_intersection<int32_t>>());
|
||||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd_fw<test_non_const_set_symmetric_difference<int32_t>>());
|
||||
|
||||
test_algo_basic_double<int32_t>(run_for_rnd_fw<test_non_const_set_union<int32_t>>());
|
||||
|
||||
std::cout << done() << std::endl;
|
||||
|
||||
|
|
|
@ -94,7 +94,7 @@ class ParanoidKey
|
|||
index = k.index;
|
||||
return *this;
|
||||
}
|
||||
ParanoidKey(int32_t index, int32_t value, OddTag) : index(index), value(value) {}
|
||||
ParanoidKey(int32_t index, int32_t value, OddTag) : value(value), index(index) {}
|
||||
ParanoidKey(ParanoidKey&& k) : value(k.value), index(k.index)
|
||||
{
|
||||
EXPECT_TRUE(k.isConstructed(), "source for move-construction is dead");
|
||||
|
@ -171,7 +171,7 @@ struct test_sort_with_compare
|
|||
typename std::enable_if<is_same_iterator_category<InputIterator, std::random_access_iterator_tag>::value,
|
||||
void>::type
|
||||
operator()(Policy&& exec, OutputIterator tmp_first, OutputIterator tmp_last, OutputIterator2 expected_first,
|
||||
OutputIterator2 expected_last, InputIterator first, InputIterator last, Size n, Compare compare)
|
||||
OutputIterator2 expected_last, InputIterator first, InputIterator, Size n, Compare compare)
|
||||
{
|
||||
using namespace std;
|
||||
copy_n(first, n, expected_first);
|
||||
|
@ -198,8 +198,8 @@ struct test_sort_with_compare
|
|||
typename Compare>
|
||||
typename std::enable_if<!is_same_iterator_category<InputIterator, std::random_access_iterator_tag>::value,
|
||||
void>::type
|
||||
operator()(Policy&& exec, OutputIterator tmp_first, OutputIterator tmp_last, OutputIterator2 expected_first,
|
||||
OutputIterator2 expected_last, InputIterator first, InputIterator last, Size n, Compare compare)
|
||||
operator()(Policy&&, OutputIterator, OutputIterator, OutputIterator2, OutputIterator2, InputIterator, InputIterator,
|
||||
Size, Compare)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -233,7 +233,7 @@ struct test_non_const
|
|||
}
|
||||
};
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
std::srand(42);
|
||||
|
|
|
@ -33,19 +33,19 @@ template <typename T>
|
|||
struct wrapper
|
||||
{
|
||||
T t;
|
||||
explicit wrapper(T t_) : t(t_) {}
|
||||
constexpr explicit wrapper(T t_) : t(t_) {}
|
||||
template <typename T2>
|
||||
wrapper(const wrapper<T2>& a)
|
||||
constexpr wrapper(const wrapper<T2>& a)
|
||||
{
|
||||
t = a.t;
|
||||
}
|
||||
template <typename T2>
|
||||
void
|
||||
constexpr void
|
||||
operator=(const wrapper<T2>& a)
|
||||
{
|
||||
t = a.t;
|
||||
}
|
||||
wrapper<T>
|
||||
constexpr wrapper<T>
|
||||
operator-(const wrapper<T>& a) const
|
||||
{
|
||||
return wrapper<T>(t - a.t);
|
||||
|
@ -75,9 +75,11 @@ compute_and_check(Iterator1 first, Iterator1 last, Iterator2 d_first, T, Functio
|
|||
if (first == last)
|
||||
return true;
|
||||
|
||||
T2 temp(*first);
|
||||
if (!compare(temp, *d_first))
|
||||
return false;
|
||||
{
|
||||
T2 temp(*first);
|
||||
if (!compare(temp, *d_first))
|
||||
return false;
|
||||
}
|
||||
Iterator1 second = std::next(first);
|
||||
|
||||
++d_first;
|
||||
|
@ -94,25 +96,25 @@ compute_and_check(Iterator1 first, Iterator1 last, Iterator2 d_first, T, Functio
|
|||
// we don't want to check equality here
|
||||
// because we can't be sure it will be strictly equal for floating point types
|
||||
template <typename Iterator1, typename Iterator2, typename T, typename Function>
|
||||
typename std::enable_if<std::is_floating_point<T>::value, bool>::type
|
||||
compute_and_check(Iterator1 first, Iterator1 last, Iterator2 d_first, T, Function)
|
||||
typename std::enable_if<std::is_floating_point<T>::value, bool>::type compute_and_check(Iterator1, Iterator1, Iterator2,
|
||||
T, Function)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
struct test_one_policy
|
||||
{
|
||||
#if _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || \
|
||||
_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN // dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || \
|
||||
defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) // dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator1, typename Iterator2, typename T, typename Function>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
operator()(__pstl::execution::unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
Iterator2 actual_e, T trash, Function f)
|
||||
{
|
||||
}
|
||||
template <typename Iterator1, typename Iterator2, typename T, typename Function>
|
||||
typename std::enable_if<is_same_iterator_category<Iterator1, std::random_access_iterator_tag>::value, void>::type
|
||||
operator()(pstl::execution::parallel_unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
operator()(__pstl::execution::parallel_unsequenced_policy, Iterator1 data_b, Iterator1 data_e, Iterator2 actual_b,
|
||||
Iterator2 actual_e, T trash, Function f)
|
||||
{
|
||||
}
|
||||
|
@ -146,16 +148,14 @@ template <typename T1, typename T2, typename Pred>
|
|||
void
|
||||
test(Pred pred)
|
||||
{
|
||||
typedef typename Sequence<T2>::iterator iterator_type;
|
||||
|
||||
const std::size_t max_len = 100000;
|
||||
|
||||
const T2 value = T2(77);
|
||||
const T1 trash = T1(31);
|
||||
static constexpr T2 value = T2(77);
|
||||
static constexpr T1 trash = T1(31);
|
||||
|
||||
Sequence<T1> actual(max_len, [](std::size_t i) { return T1(i); });
|
||||
|
||||
Sequence<T2> data(max_len, [&value](std::size_t i) { return i % 3 == 2 ? T2(i * i) : value; });
|
||||
Sequence<T2> data(max_len, [](std::size_t i) { return i % 3 == 2 ? T2(i * i) : value; });
|
||||
|
||||
for (std::size_t len = 0; len < max_len; len = len <= 16 ? len + 1 : std::size_t(3.1415 * len))
|
||||
{
|
||||
|
@ -166,7 +166,7 @@ test(Pred pred)
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test<uint8_t, uint32_t>([](uint32_t a, uint32_t b) { return a - b; });
|
||||
|
|
|
@ -62,7 +62,7 @@ test_long_form(T init, BinaryOp binary_op, F f)
|
|||
struct test_two_short_forms
|
||||
{
|
||||
|
||||
#if _PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN //dummy specialization by policy type, in case of broken configuration
|
||||
#if defined(_PSTL_ICC_16_VC14_TEST_PAR_TBB_RT_RELEASE_64_BROKEN) //dummy specialization by policy type, in case of broken configuration
|
||||
template <typename Iterator>
|
||||
void
|
||||
operator()(__pstl::execution::parallel_policy, Iterator first, Iterator last, Sum init, Sum expected)
|
||||
|
@ -105,7 +105,7 @@ test_short_forms()
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
// Test for popular types
|
||||
|
|
|
@ -108,12 +108,13 @@ struct test_scan_with_plus
|
|||
template <typename Policy, typename Iterator1, typename Iterator2, typename Iterator3, typename Size, typename T>
|
||||
void
|
||||
operator()(Policy&& exec, Iterator1 in_first, Iterator1 in_last, Iterator2 out_first, Iterator2 out_last,
|
||||
Iterator3 expected_first, Iterator3 expected_last, Size n, T init, T trash)
|
||||
Iterator3 expected_first, Iterator3, Size n, T init, T trash)
|
||||
{
|
||||
using namespace std;
|
||||
|
||||
auto orr1 = inclusive ? inclusive_scan_serial(in_first, in_last, expected_first)
|
||||
: exclusive_scan_serial(in_first, in_last, expected_first, init);
|
||||
(void)orr1;
|
||||
auto orr = inclusive ? inclusive_scan(exec, in_first, in_last, out_first)
|
||||
: exclusive_scan(exec, in_first, in_last, out_first, init);
|
||||
EXPECT_TRUE(out_last == orr,
|
||||
|
@ -146,12 +147,13 @@ struct test_scan_with_binary_op
|
|||
typename BinaryOp>
|
||||
typename std::enable_if<!TestUtils::isReverse<Iterator1>::value, void>::type
|
||||
operator()(Policy&& exec, Iterator1 in_first, Iterator1 in_last, Iterator2 out_first, Iterator2 out_last,
|
||||
Iterator3 expected_first, Iterator3 expected_last, Size n, T init, BinaryOp binary_op, T trash)
|
||||
Iterator3 expected_first, Iterator3, Size n, T init, BinaryOp binary_op, T trash)
|
||||
{
|
||||
using namespace std;
|
||||
|
||||
auto orr1 = inclusive ? inclusive_scan_serial(in_first, in_last, expected_first, binary_op, init)
|
||||
: exclusive_scan_serial(in_first, in_last, expected_first, init, binary_op);
|
||||
(void)orr1;
|
||||
auto orr = inclusive ? inclusive_scan(exec, in_first, in_last, out_first, binary_op, init)
|
||||
: exclusive_scan(exec, in_first, in_last, out_first, init, binary_op);
|
||||
|
||||
|
@ -162,8 +164,7 @@ struct test_scan_with_binary_op
|
|||
template <typename Policy, typename Iterator1, typename Iterator2, typename Iterator3, typename Size, typename T,
|
||||
typename BinaryOp>
|
||||
typename std::enable_if<TestUtils::isReverse<Iterator1>::value, void>::type
|
||||
operator()(Policy&& exec, Iterator1 in_first, Iterator1 in_last, Iterator2 out_first, Iterator2 out_last,
|
||||
Iterator3 expected_first, Iterator3 expected_last, Size n, T init, BinaryOp binary_op, T trash)
|
||||
operator()(Policy&&, Iterator1, Iterator1, Iterator2, Iterator2, Iterator3, Iterator3, Size, T, BinaryOp, T)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -186,13 +187,13 @@ test_matrix(Out init, BinaryOp binary_op, Out trash)
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
for (int32_t mode = 0; mode < 2; ++mode)
|
||||
{
|
||||
inclusive = mode != 0;
|
||||
#if !_PSTL_ICC_19_TEST_SIMD_UDS_WINDOWS_RELEASE_BROKEN
|
||||
#if !defined(_PSTL_ICC_19_TEST_SIMD_UDS_WINDOWS_RELEASE_BROKEN)
|
||||
// Test with highly restricted type and associative but not commutative operation
|
||||
test_matrix<Matrix2x2<int32_t>, Matrix2x2<int32_t>>(Matrix2x2<int32_t>(), multiply_matrix<int32_t>,
|
||||
Matrix2x2<int32_t>(-666, 666));
|
||||
|
|
|
@ -54,7 +54,7 @@ class MyClass
|
|||
int32_t my_field;
|
||||
MyClass() { my_field = 0; }
|
||||
MyClass(int32_t in) { my_field = in; }
|
||||
MyClass(const MyClass& in) { my_field = in.my_field; }
|
||||
MyClass(const MyClass& in) = default;
|
||||
|
||||
friend MyClass
|
||||
operator+(const MyClass& x, const MyClass& y)
|
||||
|
@ -66,11 +66,13 @@ class MyClass
|
|||
{
|
||||
return MyClass(-x.my_field);
|
||||
}
|
||||
friend MyClass operator*(const MyClass& x, const MyClass& y) { return MyClass(x.my_field * y.my_field); }
|
||||
bool
|
||||
operator==(const MyClass& in) const
|
||||
friend MyClass operator*(const MyClass& x, const MyClass& y)
|
||||
{
|
||||
return my_field == in.my_field;
|
||||
return MyClass(x.my_field * y.my_field);
|
||||
}
|
||||
friend bool operator==(const MyClass& x, const MyClass& y)
|
||||
{
|
||||
return x.my_field == y.my_field;
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -78,13 +80,13 @@ template <typename T>
|
|||
void
|
||||
CheckResults(const T& expected, const T& in)
|
||||
{
|
||||
EXPECT_TRUE(Equal(expected, in), "wrong result of transform_reduce");
|
||||
EXPECT_TRUE(expected == in, "wrong result of transform_reduce");
|
||||
}
|
||||
|
||||
// We need to check correctness only for "int" (for example) except cases
|
||||
// if we have "floating-point type"-specialization
|
||||
void
|
||||
CheckResults(const float32_t& expected, const float32_t& in)
|
||||
CheckResults(const float32_t&, const float32_t&)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -94,7 +96,7 @@ struct test_transform_reduce
|
|||
template <typename Policy, typename InputIterator1, typename InputIterator2, typename T, typename BinaryOperation1,
|
||||
typename BinaryOperation2, typename UnaryOp>
|
||||
void
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2 last2,
|
||||
operator()(Policy&& exec, InputIterator1 first1, InputIterator1 last1, InputIterator2 first2, InputIterator2,
|
||||
T init, BinaryOperation1 opB1, BinaryOperation2 opB2, UnaryOp opU)
|
||||
{
|
||||
|
||||
|
@ -125,20 +127,19 @@ test_by_type(T init, BinaryOperation1 opB1, BinaryOperation2 opB2, UnaryOp opU,
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
test_by_type<int32_t>(42, std::plus<int32_t>(), std::multiplies<int32_t>(), std::negate<int32_t>(),
|
||||
[](std::size_t a) -> int32_t { return int32_t(rand() % 1000); });
|
||||
[](std::size_t) -> int32_t { return int32_t(rand() % 1000); });
|
||||
test_by_type<int64_t>(0, [](const int64_t& a, const int64_t& b) -> int64_t { return a | b; }, XOR(),
|
||||
[](const int64_t& x) -> int64_t { return x * 2; },
|
||||
[](std::size_t a) -> int64_t { return int64_t(rand() % 1000); });
|
||||
test_by_type<float32_t>(1.0f, std::multiplies<float32_t>(),
|
||||
[](const float32_t& a, const float32_t& b) -> float32_t { return a + b; },
|
||||
[](const float32_t& x) -> float32_t { return x + 2; },
|
||||
[](std::size_t a) -> float32_t { return rand() % 1000; });
|
||||
[](std::size_t) -> int64_t { return int64_t(rand() % 1000); });
|
||||
test_by_type<float32_t>(
|
||||
1.0f, std::multiplies<float32_t>(), [](const float32_t& a, const float32_t& b) -> float32_t { return a + b; },
|
||||
[](const float32_t& x) -> float32_t { return x + 2; }, [](std::size_t) -> float32_t { return rand() % 1000; });
|
||||
test_by_type<MyClass>(MyClass(), std::plus<MyClass>(), std::multiplies<MyClass>(), std::negate<MyClass>(),
|
||||
[](std::size_t a) -> MyClass { return MyClass(rand() % 1000); });
|
||||
[](std::size_t) -> MyClass { return MyClass(rand() % 1000); });
|
||||
|
||||
std::cout << done() << std::endl;
|
||||
return 0;
|
||||
|
|
|
@ -47,15 +47,15 @@ struct test_transform_scan
|
|||
typename T, typename BinaryOp>
|
||||
typename std::enable_if<!TestUtils::isReverse<InputIterator>::value, void>::type
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator expected_first, OutputIterator expected_last, Size n,
|
||||
UnaryOp unary_op, T init, BinaryOp binary_op, T trash)
|
||||
OutputIterator out_last, OutputIterator expected_first, OutputIterator, Size n, UnaryOp unary_op, T init,
|
||||
BinaryOp binary_op, T trash)
|
||||
{
|
||||
using namespace std;
|
||||
|
||||
auto orr1 = inclusive ? transform_inclusive_scan(__pstl::execution::seq, first, last, expected_first, binary_op,
|
||||
unary_op, init)
|
||||
: transform_exclusive_scan(__pstl::execution::seq, first, last, expected_first, init,
|
||||
binary_op, unary_op);
|
||||
auto orr1 =
|
||||
inclusive
|
||||
? transform_inclusive_scan(std::execution::seq, first, last, expected_first, binary_op, unary_op, init)
|
||||
: transform_exclusive_scan(std::execution::seq, first, last, expected_first, init, binary_op, unary_op);
|
||||
auto orr2 = inclusive ? transform_inclusive_scan(exec, first, last, out_first, binary_op, unary_op, init)
|
||||
: transform_exclusive_scan(exec, first, last, out_first, init, binary_op, unary_op);
|
||||
EXPECT_TRUE(out_last == orr2, "transform...scan returned wrong iterator");
|
||||
|
@ -64,7 +64,7 @@ struct test_transform_scan
|
|||
// Checks inclusive scan if init is not provided
|
||||
if (inclusive && n > 0)
|
||||
{
|
||||
orr1 = transform_inclusive_scan(__pstl::execution::seq, first, last, expected_first, binary_op, unary_op);
|
||||
orr1 = transform_inclusive_scan(std::execution::seq, first, last, expected_first, binary_op, unary_op);
|
||||
orr2 = transform_inclusive_scan(exec, first, last, out_first, binary_op, unary_op);
|
||||
EXPECT_TRUE(out_last == orr2, "transform...scan returned wrong iterator");
|
||||
check_and_reset(expected_first, out_first, n, trash);
|
||||
|
@ -74,9 +74,8 @@ struct test_transform_scan
|
|||
template <typename Policy, typename InputIterator, typename OutputIterator, typename Size, typename UnaryOp,
|
||||
typename T, typename BinaryOp>
|
||||
typename std::enable_if<TestUtils::isReverse<InputIterator>::value, void>::type
|
||||
operator()(Policy&& exec, InputIterator first, InputIterator last, OutputIterator out_first,
|
||||
OutputIterator out_last, OutputIterator expected_first, OutputIterator expected_last, Size n,
|
||||
UnaryOp unary_op, T init, BinaryOp binary_op, T trash)
|
||||
operator()(Policy&&, InputIterator, InputIterator, OutputIterator, OutputIterator, OutputIterator, OutputIterator,
|
||||
Size, UnaryOp, T, BinaryOp, T)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
@ -140,6 +139,7 @@ test(UnaryOp unary_op, Out init, BinaryOp binary_op, Out trash)
|
|||
inclusive
|
||||
? transform_inclusive_scan_serial(in.cbegin(), in.cend(), out.fbegin(), unary_op, init, binary_op)
|
||||
: transform_exclusive_scan_serial(in.cbegin(), in.cend(), out.fbegin(), unary_op, init, binary_op);
|
||||
(void)result;
|
||||
check_and_reset(expected.begin(), out.begin(), out.size(), trash);
|
||||
|
||||
invoke_on_all_policies(test_transform_scan(), in.begin(), in.end(), out.begin(), out.end(), expected.begin(),
|
||||
|
@ -167,13 +167,13 @@ test_matrix(UnaryOp unary_op, Out init, BinaryOp binary_op, Out trash)
|
|||
}
|
||||
}
|
||||
|
||||
int32_t
|
||||
int
|
||||
main()
|
||||
{
|
||||
for (int32_t mode = 0; mode < 2; ++mode)
|
||||
{
|
||||
inclusive = mode != 0;
|
||||
#if !_PSTL_ICC_19_TEST_SIMD_UDS_WINDOWS_RELEASE_BROKEN
|
||||
#if !defined(_PSTL_ICC_19_TEST_SIMD_UDS_WINDOWS_RELEASE_BROKEN)
|
||||
test_matrix<Matrix2x2<int32_t>, Matrix2x2<int32_t>>([](const Matrix2x2<int32_t> x) { return x; },
|
||||
Matrix2x2<int32_t>(), multiply_matrix<int32_t>,
|
||||
Matrix2x2<int32_t>(-666, 666));
|
||||
|
|
|
@ -30,7 +30,7 @@ typedef float float32_t;
|
|||
|
||||
template <class T, std::size_t N>
|
||||
constexpr size_t
|
||||
const_size(const T (&array)[N]) noexcept
|
||||
const_size(const T (&)[N]) noexcept
|
||||
{
|
||||
return N;
|
||||
}
|
||||
|
@ -119,7 +119,7 @@ expect_equal(Iterator1 expected_first, Iterator2 actual_first, Size n, const cha
|
|||
const char* message)
|
||||
{
|
||||
size_t error_count = 0;
|
||||
for (size_t k = 0; k < n && error_count < 10; ++k, ++expected_first, ++actual_first)
|
||||
for (Size k = 0; k < n && error_count < 10; ++k, ++expected_first, ++actual_first)
|
||||
{
|
||||
if (!(*expected_first == *actual_first))
|
||||
{
|
||||
|
@ -231,6 +231,82 @@ fill_data(Iterator first, Iterator last, F f)
|
|||
}
|
||||
}
|
||||
|
||||
struct MemoryChecker {
|
||||
// static counters and state tags
|
||||
static std::atomic<std::int64_t> alive_object_counter; // initialized outside
|
||||
static constexpr std::int64_t alive_state = 0xAAAAAAAAAAAAAAAA;
|
||||
static constexpr std::int32_t dead_state = 0; // only used as a set value to cancel alive_state
|
||||
|
||||
std::int32_t _value; // object value used for algorithms
|
||||
std::int64_t _state; // state tag used for checks
|
||||
|
||||
// ctors, dtors, assign ops
|
||||
explicit MemoryChecker(std::int32_t value = 0) : _value(value) {
|
||||
// check for EXPECT_TRUE(state() != alive_state, ...) has not been done since we cannot guarantee that
|
||||
// raw memory for object being constructed does not have a bit sequence being equal to alive_state
|
||||
|
||||
// set constructed state and increment counter for living object
|
||||
inc_alive_objects();
|
||||
_state = alive_state;
|
||||
}
|
||||
MemoryChecker(MemoryChecker&& other) : _value(other.value()) {
|
||||
// check for EXPECT_TRUE(state() != alive_state, ...) has not been done since
|
||||
// compiler can optimize out the move ctor call that results in false positive failure
|
||||
EXPECT_TRUE(other.state() == alive_state, "wrong effect from MemoryChecker(MemoryChecker&&): attemp to construct an object from non-existing object");
|
||||
// set constructed state and increment counter for living object
|
||||
inc_alive_objects();
|
||||
_state = alive_state;
|
||||
}
|
||||
MemoryChecker(const MemoryChecker& other) : _value(other.value()) {
|
||||
// check for EXPECT_TRUE(state() != alive_state, ...) has not been done since
|
||||
// compiler can optimize out the copy ctor call that results in false positive failure
|
||||
EXPECT_TRUE(other.state() == alive_state, "wrong effect from MemoryChecker(const MemoryChecker&): attemp to construct an object from non-existing object");
|
||||
// set constructed state and increment counter for living object
|
||||
inc_alive_objects();
|
||||
_state = alive_state;
|
||||
}
|
||||
MemoryChecker& operator=(MemoryChecker&& other) {
|
||||
// check if we do not assign over uninitialized memory
|
||||
EXPECT_TRUE(state() == alive_state, "wrong effect from MemoryChecker::operator=(MemoryChecker&& other): attemp to assign to non-existing object");
|
||||
EXPECT_TRUE(other.state() == alive_state, "wrong effect from MemoryChecker::operator=(MemoryChecker&& other): attemp to assign from non-existing object");
|
||||
// just assign new value, counter is the same, state is the same
|
||||
_value = other.value();
|
||||
|
||||
return *this;
|
||||
}
|
||||
MemoryChecker& operator=(const MemoryChecker& other) {
|
||||
// check if we do not assign over uninitialized memory
|
||||
EXPECT_TRUE(state() == alive_state, "wrong effect from MemoryChecker::operator=(const MemoryChecker& other): attemp to assign to non-existing object");
|
||||
EXPECT_TRUE(other.state() == alive_state, "wrong effect from MemoryChecker::operator=(const MemoryChecker& other): attemp to assign from non-existing object");
|
||||
// just assign new value, counter is the same, state is the same
|
||||
_value = other.value();
|
||||
|
||||
return *this;
|
||||
}
|
||||
~MemoryChecker() {
|
||||
// check if we do not double destruct the object
|
||||
EXPECT_TRUE(state() == alive_state, "wrong effect from ~MemoryChecker(): attemp to destroy non-existing object");
|
||||
// set destructed state and decrement counter for living object
|
||||
static_cast<volatile std::int64_t&>(_state) = dead_state;
|
||||
dec_alive_objects();
|
||||
}
|
||||
|
||||
// getters
|
||||
std::int32_t value() const { return _value; }
|
||||
std::int64_t state() const { return _state; }
|
||||
static std::int32_t alive_objects() { return alive_object_counter.load(); }
|
||||
private:
|
||||
// setters
|
||||
void inc_alive_objects() { alive_object_counter.fetch_add(1); }
|
||||
void dec_alive_objects() { alive_object_counter.fetch_sub(1); }
|
||||
};
|
||||
|
||||
std::atomic<std::int64_t> MemoryChecker::alive_object_counter{0};
|
||||
|
||||
std::ostream& operator<<(std::ostream& os, const MemoryChecker& val) { return (os << val.value()); }
|
||||
bool operator==(const MemoryChecker& v1, const MemoryChecker& v2) { return v1.value() == v2.value(); }
|
||||
bool operator<(const MemoryChecker& v1, const MemoryChecker& v2) { return v1.value() < v2.value(); }
|
||||
|
||||
// Sequence<T> is a container of a sequence of T with lots of kinds of iterators.
|
||||
// Prefixes on begin/end mean:
|
||||
// c = "const"
|
||||
|
@ -572,7 +648,7 @@ struct Matrix2x2
|
|||
T a[2][2];
|
||||
Matrix2x2() : a{{1, 0}, {0, 1}} {}
|
||||
Matrix2x2(T x, T y) : a{{0, x}, {x, y}} {}
|
||||
#if !_PSTL_ICL_19_VC14_VC141_TEST_SCAN_RELEASE_BROKEN
|
||||
#if !defined(_PSTL_ICL_19_VC14_VC141_TEST_SCAN_RELEASE_BROKEN)
|
||||
Matrix2x2(const Matrix2x2& m) : a{{m.a[0][0], m.a[0][1]}, {m.a[1][0], m.a[1][1]}} {}
|
||||
Matrix2x2&
|
||||
operator=(const Matrix2x2& m)
|
||||
|
@ -651,7 +727,7 @@ struct ReverseAdapter
|
|||
iterator_type
|
||||
operator()(Iterator it)
|
||||
{
|
||||
#if _PSTL_CPP14_MAKE_REVERSE_ITERATOR_PRESENT
|
||||
#if defined(_PSTL_CPP14_MAKE_REVERSE_ITERATOR_PRESENT)
|
||||
return std::make_reverse_iterator(it);
|
||||
#else
|
||||
return iterator_type(it);
|
||||
|
@ -1191,7 +1267,7 @@ transform_reduce_serial(InputIterator first, InputIterator last, T init, BinaryO
|
|||
static const char*
|
||||
done()
|
||||
{
|
||||
#if _PSTL_TEST_SUCCESSFUL_KEYWORD
|
||||
#if defined(_PSTL_TEST_SUCCESSFUL_KEYWORD)
|
||||
return "done";
|
||||
#else
|
||||
return "passed";
|
||||
|
@ -1228,8 +1304,12 @@ template <typename Policy, typename F>
|
|||
static void
|
||||
invoke_if(Policy&&, F f)
|
||||
{
|
||||
#if _PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN || _PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN
|
||||
__pstl::__internal::invoke_if_not(__pstl::__internal::allow_unsequenced<Policy>(), f);
|
||||
#if defined(_PSTL_ICC_16_VC14_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN) || defined(_PSTL_ICC_17_VC141_TEST_SIMD_LAMBDA_DEBUG_32_BROKEN)
|
||||
using decay_policy = typename std::decay<Policy>::type;
|
||||
using allow_unsequenced =
|
||||
std::integral_constant<bool, (std::is_same<decay_policy, std::execution::unsequenced_policy>::value ||
|
||||
std::is_same<decay_policy, std::execution::parallel_unsequenced_policy>::value)>;
|
||||
__pstl::__internal::__invoke_if_not(allow_unsequenced{}, f);
|
||||
#else
|
||||
f();
|
||||
#endif
|
||||
|
|
Loading…
Add table
Reference in a new issue