mirror of
https://github.com/boostorg/compute.git
synced 2026-02-19 14:22:12 +00:00
Use radix_sort() for stable_sort() when possible
This commit is contained in:
@@ -23,6 +23,8 @@
|
||||
#include <boost/compute/algorithm/exclusive_scan.hpp>
|
||||
#include <boost/compute/container/vector.hpp>
|
||||
#include <boost/compute/type_traits/type_name.hpp>
|
||||
#include <boost/compute/type_traits/is_fundamental.hpp>
|
||||
#include <boost/compute/type_traits/is_vector_type.hpp>
|
||||
#include <boost/compute/detail/iterator_range_size.hpp>
|
||||
#include <boost/compute/detail/program_cache.hpp>
|
||||
|
||||
@@ -30,6 +32,16 @@ namespace boost {
|
||||
namespace compute {
|
||||
namespace detail {
|
||||
|
||||
// meta-function returning true if type T is radix-sortable
|
||||
template<class T>
|
||||
struct is_radix_sortable :
|
||||
boost::mpl::and_<
|
||||
typename ::boost::compute::is_fundamental<T>::type,
|
||||
typename boost::mpl::not_<typename is_vector_type<T>::type>::type
|
||||
>
|
||||
{
|
||||
};
|
||||
|
||||
template<size_t N>
|
||||
struct radix_sort_value_type
|
||||
{
|
||||
|
||||
@@ -15,10 +15,51 @@
|
||||
|
||||
#include <boost/compute/system.hpp>
|
||||
#include <boost/compute/command_queue.hpp>
|
||||
#include <boost/compute/algorithm/detail/radix_sort.hpp>
|
||||
#include <boost/compute/algorithm/detail/insertion_sort.hpp>
|
||||
#include <boost/compute/algorithm/reverse.hpp>
|
||||
#include <boost/compute/functional/operator.hpp>
|
||||
|
||||
namespace boost {
|
||||
namespace compute {
|
||||
namespace detail {
|
||||
|
||||
template<class Iterator, class Compare>
|
||||
inline void dispatch_stable_sort(Iterator first,
|
||||
Iterator last,
|
||||
Compare compare,
|
||||
command_queue &queue)
|
||||
{
|
||||
::boost::compute::detail::serial_insertion_sort(
|
||||
first, last, compare, queue
|
||||
);
|
||||
}
|
||||
|
||||
template<class T>
|
||||
inline typename boost::enable_if_c<is_radix_sortable<T>::value>::type
|
||||
dispatch_stable_sort(buffer_iterator<T> first,
|
||||
buffer_iterator<T> last,
|
||||
less<T>,
|
||||
command_queue &queue)
|
||||
{
|
||||
::boost::compute::detail::radix_sort(first, last, queue);
|
||||
}
|
||||
|
||||
template<class T>
|
||||
inline typename boost::enable_if_c<is_radix_sortable<T>::value>::type
|
||||
dispatch_stable_sort(buffer_iterator<T> first,
|
||||
buffer_iterator<T> last,
|
||||
greater<T>,
|
||||
command_queue &queue)
|
||||
{
|
||||
// radix sort in ascending order
|
||||
::boost::compute::detail::radix_sort(first, last, queue);
|
||||
|
||||
// reverse range to descending order
|
||||
::boost::compute::reverse(first, last, queue);
|
||||
}
|
||||
|
||||
} // end detail namespace
|
||||
|
||||
/// Sorts the values in the range [\p first, \p last) according to
|
||||
/// \p compare. The relative order of identical values is preserved.
|
||||
@@ -30,10 +71,9 @@ inline void stable_sort(Iterator first,
|
||||
Compare compare,
|
||||
command_queue &queue = system::default_queue())
|
||||
{
|
||||
return ::boost::compute::detail::serial_insertion_sort(first,
|
||||
last,
|
||||
compare,
|
||||
queue);
|
||||
::boost::compute::detail::dispatch_stable_sort(
|
||||
first, last, compare, queue
|
||||
);
|
||||
}
|
||||
|
||||
/// \overload
|
||||
@@ -46,7 +86,7 @@ inline void stable_sort(Iterator first,
|
||||
|
||||
::boost::compute::less<value_type> less;
|
||||
|
||||
return ::boost::compute::stable_sort(first, last, less, queue);
|
||||
::boost::compute::stable_sort(first, last, less, queue);
|
||||
}
|
||||
|
||||
} // end compute namespace
|
||||
|
||||
@@ -11,6 +11,8 @@
|
||||
#ifndef BOOST_COMPUTE_TYPE_TRAITS_IS_VECTOR_TYPE_HPP
|
||||
#define BOOST_COMPUTE_TYPE_TRAITS_IS_VECTOR_TYPE_HPP
|
||||
|
||||
#include <boost/mpl/bool.hpp>
|
||||
|
||||
#include <boost/compute/type_traits/vector_size.hpp>
|
||||
|
||||
namespace boost {
|
||||
@@ -26,10 +28,8 @@ namespace compute {
|
||||
///
|
||||
/// \see make_vector_type, vector_size
|
||||
template<class T>
|
||||
struct is_vector_type
|
||||
struct is_vector_type : boost::mpl::bool_<vector_size<T>::value != 1>
|
||||
{
|
||||
/// \internal_
|
||||
BOOST_STATIC_CONSTANT(bool, value = (vector_size<T>::value != 1));
|
||||
};
|
||||
|
||||
} // end compute namespace
|
||||
|
||||
Reference in New Issue
Block a user