You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

94 lines
3.4KB

  1. /// \file
  2. // Range v3 library
  3. //
  4. // Copyright Eric Niebler 2013-present
  5. //
  6. // Use, modification and distribution is subject to the
  7. // Boost Software License, Version 1.0. (See accompanying
  8. // file LICENSE_1_0.txt or copy at
  9. // http://www.boost.org/LICENSE_1_0.txt)
  10. //
  11. // Project home: https://github.com/ericniebler/range-v3
  12. //
  13. #ifndef RANGES_V3_ALGORITHM_SWAP_RANGES_HPP
  14. #define RANGES_V3_ALGORITHM_SWAP_RANGES_HPP
  15. #include <range/v3/range_fwd.hpp>
  16. #include <range/v3/algorithm/result_types.hpp>
  17. #include <range/v3/iterator/concepts.hpp>
  18. #include <range/v3/iterator/traits.hpp>
  19. #include <range/v3/range/access.hpp>
  20. #include <range/v3/range/concepts.hpp>
  21. #include <range/v3/range/dangling.hpp>
  22. #include <range/v3/range/traits.hpp>
  23. #include <range/v3/utility/static_const.hpp>
  24. namespace ranges
  25. {
  26. /// \addtogroup group-algorithms
  27. /// @{
  28. template<typename I1, typename I2>
  29. using swap_ranges_result = detail::in1_in2_result<I1, I2>;
  30. RANGES_BEGIN_NIEBLOID(swap_ranges)
  31. /// \brief function template \c swap_ranges
  32. template<typename I1, typename S1, typename I2>
  33. auto RANGES_FUN_NIEBLOID(swap_ranges)(I1 begin1, S1 end1, I2 begin2) //
  34. ->CPP_ret(swap_ranges_result<I1, I2>)( //
  35. requires input_iterator<I1> && sentinel_for<S1, I1> &&
  36. input_iterator<I2> && indirectly_swappable<I1, I2>)
  37. {
  38. for(; begin1 != end1; ++begin1, ++begin2)
  39. ranges::iter_swap(begin1, begin2);
  40. return {begin1, begin2};
  41. }
  42. /// \overload
  43. template<typename I1, typename S1, typename I2, typename S2>
  44. auto RANGES_FUN_NIEBLOID(swap_ranges)(I1 begin1,
  45. S1 end1,
  46. I2 begin2,
  47. S2 end2) //
  48. ->CPP_ret(swap_ranges_result<I1, I2>)( //
  49. requires input_iterator<I1> && sentinel_for<S1, I1> &&
  50. input_iterator<I2> && sentinel_for<S2, I2> &&
  51. indirectly_swappable<I1, I2>)
  52. {
  53. for(; begin1 != end1 && begin2 != end2; ++begin1, ++begin2)
  54. ranges::iter_swap(begin1, begin2);
  55. return {begin1, begin2};
  56. }
  57. template<typename Rng1, typename I2_>
  58. auto RANGES_FUN_NIEBLOID(swap_ranges)(Rng1 && rng1, I2_ && begin2) //
  59. ->CPP_ret(swap_ranges_result<iterator_t<Rng1>, uncvref_t<I2_>>)( //
  60. requires input_range<Rng1> && input_iterator<uncvref_t<I2_>> &&
  61. indirectly_swappable<iterator_t<Rng1>, uncvref_t<I2_>>)
  62. {
  63. return (*this)(begin(rng1), end(rng1), (I2_ &&) begin2);
  64. }
  65. template<typename Rng1, typename Rng2>
  66. auto RANGES_FUN_NIEBLOID(swap_ranges)(Rng1 && rng1, Rng2 && rng2) //
  67. ->CPP_ret(
  68. swap_ranges_result<safe_iterator_t<Rng1>, safe_iterator_t<Rng2>>)( //
  69. requires input_range<Rng1> && input_range<Rng2> &&
  70. indirectly_swappable<iterator_t<Rng1>, iterator_t<Rng2>>)
  71. {
  72. return (*this)(begin(rng1), end(rng1), begin(rng2), end(rng2));
  73. }
  74. RANGES_END_NIEBLOID(swap_ranges)
  75. namespace cpp20
  76. {
  77. using ranges::swap_ranges;
  78. using ranges::swap_ranges_result;
  79. } // namespace cpp20
  80. /// @}
  81. } // namespace ranges
  82. #endif // include guard