include/boost/capy/detail/owned_range.hpp

100.0% Lines (8 / 8) 100.0% Functions (1 / 1, 1 excl)
owned_range.hpp
f(x) Functions (2)
Line TLA Hits Source Code
1 //
2 // Copyright (c) 2026 Steve Gerbino
3 //
4 // Distributed under the Boost Software License, Version 1.0. (See accompanying
5 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6 //
7 // Official repository: https://github.com/cppalliance/capy
8 //
9
10 #ifndef BOOST_CAPY_DETAIL_OWNED_RANGE_HPP
11 #define BOOST_CAPY_DETAIL_OWNED_RANGE_HPP
12
13 #include <boost/capy/detail/config.hpp>
14
15 #include <ranges>
16 #include <type_traits>
17 #include <utility>
18 #include <vector>
19
20 namespace boost {
21 namespace capy {
22 namespace detail {
23
24 // A join's runners refer to their awaitables in place until they start,
25 // so the range it owns must yield lvalues that outlive the iteration.
26 // Only a forward range guarantees that: an input iterator may hold the
27 // element it yields and replace it on the next step. Any other range is
28 // moved into a vector instead.
29 template<class R>
30 using owned_range_t = std::conditional_t<
31 std::ranges::forward_range<std::remove_cvref_t<R>&> &&
32 std::is_lvalue_reference_v<
33 std::ranges::range_reference_t<std::remove_cvref_t<R>&>>,
34 std::remove_cvref_t<R>,
35 std::vector<std::ranges::range_value_t<R>>>;
36
37 template<class R>
38 owned_range_t<R>
39 41x own_range(R&& r)
40 {
41 if constexpr(std::is_same_v<owned_range_t<R>, std::remove_cvref_t<R>>)
42 {
43 36x return std::forward<R>(r);
44 }
45 else
46 {
47 5x owned_range_t<R> v;
48 5x v.reserve(std::ranges::size(r));
49 34x for(auto&& a : r)
50 13x v.push_back(std::move(a));
51 8x return v;
52 5x }
53 }
54
55 } // namespace detail
56 } // namespace capy
57 } // namespace boost
58
59 #endif
60