stable_partition.hpp 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778
  1. //---------------------------------------------------------------------------//
  2. // Copyright (c) 2014 Roshan <thisisroshansmail@gmail.com>
  3. //
  4. // Distributed under the Boost Software License, Version 1.0
  5. // See accompanying file LICENSE_1_0.txt or copy at
  6. // http://www.boost.org/LICENSE_1_0.txt
  7. //
  8. // See http://boostorg.github.com/compute for more information.
  9. //---------------------------------------------------------------------------//
  10. #ifndef BOOST_COMPUTE_ALGORITHM_STABLE_PARTITION_HPP
  11. #define BOOST_COMPUTE_ALGORITHM_STABLE_PARTITION_HPP
  12. #include <boost/static_assert.hpp>
  13. #include <boost/compute/system.hpp>
  14. #include <boost/compute/context.hpp>
  15. #include <boost/compute/functional.hpp>
  16. #include <boost/compute/command_queue.hpp>
  17. #include <boost/compute/algorithm/copy_if.hpp>
  18. #include <boost/compute/container/vector.hpp>
  19. #include <boost/compute/type_traits/is_device_iterator.hpp>
  20. namespace boost {
  21. namespace compute {
  22. ///
  23. /// \brief Partitioning algorithm
  24. ///
  25. /// Partitions the elements in the range [\p first, \p last) according to
  26. /// \p predicate. The order of the elements is preserved.
  27. /// \return Iterator pointing to end of true values
  28. ///
  29. /// \param first Iterator pointing to start of range
  30. /// \param last Iterator pointing to end of range
  31. /// \param predicate Unary predicate to be applied on each element
  32. /// \param queue Queue on which to execute
  33. ///
  34. /// Space complexity: \Omega(3n)
  35. ///
  36. /// \see is_partitioned() and partition()
  37. ///
  38. template<class Iterator, class UnaryPredicate>
  39. inline Iterator stable_partition(Iterator first,
  40. Iterator last,
  41. UnaryPredicate predicate,
  42. command_queue &queue = system::default_queue())
  43. {
  44. BOOST_STATIC_ASSERT(is_device_iterator<Iterator>::value);
  45. typedef typename std::iterator_traits<Iterator>::value_type value_type;
  46. // make temporary copy of the input
  47. ::boost::compute::vector<value_type> tmp(first, last, queue);
  48. // copy true values
  49. Iterator last_true =
  50. ::boost::compute::copy_if(tmp.begin(),
  51. tmp.end(),
  52. first,
  53. predicate,
  54. queue);
  55. // copy false values
  56. Iterator last_false =
  57. ::boost::compute::copy_if(tmp.begin(),
  58. tmp.end(),
  59. last_true,
  60. not1(predicate),
  61. queue);
  62. // return iterator pointing to the last true value
  63. return last_true;
  64. }
  65. } // end compute namespace
  66. } // end boost namespace
  67. #endif // BOOST_COMPUTE_ALGORITHM_STABLE_PARTITION_HPP