tmp/tmp3hwxctj2/{from.md → to.md}
RENAMED
|
@@ -1,41 +1,56 @@
|
|
| 1 |
### Take view <a id="range.take">[[range.take]]</a>
|
| 2 |
|
| 3 |
#### Overview <a id="range.take.overview">[[range.take.overview]]</a>
|
| 4 |
|
| 5 |
-
`take_view` produces a
|
| 6 |
-
|
| 7 |
|
| 8 |
The name `views::take` denotes a range adaptor object
|
| 9 |
[[range.adaptor.object]]. Let `E` and `F` be expressions, let `T` be
|
| 10 |
`remove_cvref_t<decltype((E))>`, and let `D` be
|
| 11 |
`range_difference_t<decltype((E))>`. If `decltype((F))` does not model
|
| 12 |
`convertible_to<D>`, `views::take(E, F)` is ill-formed. Otherwise, the
|
| 13 |
expression `views::take(E, F)` is expression-equivalent to:
|
| 14 |
|
| 15 |
-
- If `T` is a specialization of `
|
| 16 |
-
|
|
|
|
| 17 |
- Otherwise, if `T` models `random_access_range` and `sized_range` and
|
| 18 |
-
is
|
| 19 |
-
|
| 20 |
-
|
| 21 |
-
|
| 22 |
-
|
| 23 |
-
- a specialization of `
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 24 |
|
| 25 |
-
|
| 26 |
-
`
|
| 27 |
-
|
| 28 |
-
- Otherwise, `ranges::take_view{E, F}`.
|
| 29 |
|
| 30 |
[*Example 1*:
|
| 31 |
|
| 32 |
``` cpp
|
| 33 |
vector<int> is{0,1,2,3,4,5,6,7,8,9};
|
| 34 |
-
|
| 35 |
-
|
| 36 |
-
cout << i << ' '; // prints: 0 1 2 3 4
|
| 37 |
```
|
| 38 |
|
| 39 |
— *end example*]
|
| 40 |
|
| 41 |
#### Class template `take_view` <a id="range.take.view">[[range.take.view]]</a>
|
|
@@ -45,62 +60,80 @@ namespace std::ranges {
|
|
| 45 |
template<view V>
|
| 46 |
class take_view : public view_interface<take_view<V>> {
|
| 47 |
private:
|
| 48 |
V base_ = V(); // exposition only
|
| 49 |
range_difference_t<V> count_ = 0; // exposition only
|
|
|
|
| 50 |
// [range.take.sentinel], class template take_view::sentinel
|
| 51 |
-
template<bool>
|
|
|
|
| 52 |
public:
|
| 53 |
-
take_view() = default;
|
| 54 |
-
constexpr take_view(V base, range_difference_t<V> count);
|
| 55 |
|
| 56 |
constexpr V base() const & requires copy_constructible<V> { return base_; }
|
| 57 |
constexpr V base() && { return std::move(base_); }
|
| 58 |
|
| 59 |
constexpr auto begin() requires (!simple-view<V>) {
|
| 60 |
if constexpr (sized_range<V>) {
|
| 61 |
-
if constexpr (random_access_range<V>)
|
| 62 |
return ranges::begin(base_);
|
| 63 |
-
else {
|
| 64 |
-
auto sz = size();
|
| 65 |
-
return counted_iterator
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 66 |
}
|
| 67 |
-
} else
|
| 68 |
-
return counted_iterator{ranges::begin(base_), count_};
|
| 69 |
}
|
| 70 |
|
| 71 |
constexpr auto begin() const requires range<const V> {
|
| 72 |
if constexpr (sized_range<const V>) {
|
| 73 |
-
if constexpr (random_access_range<const V>)
|
| 74 |
return ranges::begin(base_);
|
| 75 |
-
else {
|
| 76 |
-
auto sz = size();
|
| 77 |
-
return counted_iterator
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 78 |
}
|
| 79 |
-
} else
|
| 80 |
-
return counted_iterator{ranges::begin(base_), count_};
|
| 81 |
}
|
| 82 |
|
| 83 |
constexpr auto end() requires (!simple-view<V>) {
|
| 84 |
if constexpr (sized_range<V>) {
|
| 85 |
if constexpr (random_access_range<V>)
|
| 86 |
-
return ranges::begin(base_) + size();
|
| 87 |
else
|
| 88 |
return default_sentinel;
|
| 89 |
-
} else
|
|
|
|
|
|
|
| 90 |
return sentinel<false>{ranges::end(base_)};
|
| 91 |
}
|
|
|
|
| 92 |
|
| 93 |
constexpr auto end() const requires range<const V> {
|
| 94 |
if constexpr (sized_range<const V>) {
|
| 95 |
if constexpr (random_access_range<const V>)
|
| 96 |
-
return ranges::begin(base_) + size();
|
| 97 |
else
|
| 98 |
return default_sentinel;
|
| 99 |
-
} else
|
|
|
|
|
|
|
| 100 |
return sentinel<true>{ranges::end(base_)};
|
| 101 |
}
|
|
|
|
| 102 |
|
| 103 |
constexpr auto size() requires sized_range<V> {
|
| 104 |
auto n = ranges::size(base_);
|
| 105 |
return ranges::min(n, static_cast<decltype(n)>(count_));
|
| 106 |
}
|
|
@@ -109,20 +142,22 @@ namespace std::ranges {
|
|
| 109 |
auto n = ranges::size(base_);
|
| 110 |
return ranges::min(n, static_cast<decltype(n)>(count_));
|
| 111 |
}
|
| 112 |
};
|
| 113 |
|
| 114 |
-
template<
|
| 115 |
take_view(R&&, range_difference_t<R>)
|
| 116 |
-> take_view<views::all_t<R>>;
|
| 117 |
}
|
| 118 |
```
|
| 119 |
|
| 120 |
``` cpp
|
| 121 |
-
constexpr take_view(V base, range_difference_t<V> count);
|
| 122 |
```
|
| 123 |
|
|
|
|
|
|
|
| 124 |
*Effects:* Initializes *base\_* with `std::move(base)` and *count\_*
|
| 125 |
with `count`.
|
| 126 |
|
| 127 |
#### Class template `take_view::sentinel` <a id="range.take.sentinel">[[range.take.sentinel]]</a>
|
| 128 |
|
|
@@ -130,22 +165,28 @@ with `count`.
|
|
| 130 |
namespace std::ranges {
|
| 131 |
template<view V>
|
| 132 |
template<bool Const>
|
| 133 |
class take_view<V>::sentinel {
|
| 134 |
private:
|
| 135 |
-
using Base =
|
| 136 |
-
|
|
|
|
| 137 |
sentinel_t<Base> end_ = sentinel_t<Base>(); // exposition only
|
|
|
|
| 138 |
public:
|
| 139 |
sentinel() = default;
|
| 140 |
constexpr explicit sentinel(sentinel_t<Base> end);
|
| 141 |
constexpr sentinel(sentinel<!Const> s)
|
| 142 |
requires Const && convertible_to<sentinel_t<V>, sentinel_t<Base>>;
|
| 143 |
|
| 144 |
constexpr sentinel_t<Base> base() const;
|
| 145 |
|
| 146 |
-
friend constexpr bool operator==(const CI& y, const sentinel& x);
|
|
|
|
|
|
|
|
|
|
|
|
|
| 147 |
};
|
| 148 |
}
|
| 149 |
```
|
| 150 |
|
| 151 |
``` cpp
|
|
@@ -166,11 +207,15 @@ constexpr sentinel_t<Base> base() const;
|
|
| 166 |
```
|
| 167 |
|
| 168 |
*Effects:* Equivalent to: `return `*`end_`*`;`
|
| 169 |
|
| 170 |
``` cpp
|
| 171 |
-
friend constexpr bool operator==(const CI& y, const sentinel& x);
|
|
|
|
|
|
|
|
|
|
|
|
|
| 172 |
```
|
| 173 |
|
| 174 |
*Effects:* Equivalent to:
|
| 175 |
`return y.count() == 0 || y.base() == x.`*`end_`*`;`
|
| 176 |
|
|
|
|
| 1 |
### Take view <a id="range.take">[[range.take]]</a>
|
| 2 |
|
| 3 |
#### Overview <a id="range.take.overview">[[range.take.overview]]</a>
|
| 4 |
|
| 5 |
+
`take_view` produces a view of the first N elements from another view,
|
| 6 |
+
or all the elements if the adapted view contains fewer than N.
|
| 7 |
|
| 8 |
The name `views::take` denotes a range adaptor object
|
| 9 |
[[range.adaptor.object]]. Let `E` and `F` be expressions, let `T` be
|
| 10 |
`remove_cvref_t<decltype((E))>`, and let `D` be
|
| 11 |
`range_difference_t<decltype((E))>`. If `decltype((F))` does not model
|
| 12 |
`convertible_to<D>`, `views::take(E, F)` is ill-formed. Otherwise, the
|
| 13 |
expression `views::take(E, F)` is expression-equivalent to:
|
| 14 |
|
| 15 |
+
- If `T` is a specialization of `empty_view` [[range.empty.view]], then
|
| 16 |
+
`((void)F, decay-copy(E))`, except that the evaluations of `E` and `F`
|
| 17 |
+
are indeterminately sequenced.
|
| 18 |
- Otherwise, if `T` models `random_access_range` and `sized_range` and
|
| 19 |
+
is a specialization of `span` [[views.span]], `basic_string_view`
|
| 20 |
+
[[string.view]], or `subrange` [[range.subrange]], then
|
| 21 |
+
`U(ranges::begin(E),
|
| 22 |
+
ranges::begin(E) + std::min<D>(ranges::distance(E), F))`, except that
|
| 23 |
+
`E` is evaluated only once, where `U` is a type determined as follows:
|
| 24 |
+
- if `T` is a specialization of `span`, then `U` is
|
| 25 |
+
`span<typename T::element_type>`;
|
| 26 |
+
- otherwise, if `T` is a specialization of `basic_string_view`, then
|
| 27 |
+
`U` is `T`;
|
| 28 |
+
- otherwise, `T` is a specialization of `subrange`, and `U` is
|
| 29 |
+
`subrange<iterator_t<T>>`;
|
| 30 |
+
- otherwise, if `T` is a specialization of `iota_view`
|
| 31 |
+
[[range.iota.view]] that models `random_access_range` and
|
| 32 |
+
`sized_range`, then `iota_view(*ranges::begin(E),
|
| 33 |
+
*(ranges::begin(E) + std::{}min<D>(ranges::distance(E), F)))`, except
|
| 34 |
+
that `E` is evaluated only once.
|
| 35 |
+
- Otherwise, if `T` is a specialization of `repeat_view`
|
| 36 |
+
[[range.repeat.view]]:
|
| 37 |
+
- if `T` models `sized_range`, then
|
| 38 |
+
``` cpp
|
| 39 |
+
views::repeat(*E.value_, std::min<D>(ranges::distance(E), F))
|
| 40 |
+
```
|
| 41 |
|
| 42 |
+
except that `E` is evaluated only once;
|
| 43 |
+
- otherwise, `views::repeat(*E.value_, static_cast<D>(F))`.
|
| 44 |
+
- Otherwise, `take_view(E, F)`.
|
|
|
|
| 45 |
|
| 46 |
[*Example 1*:
|
| 47 |
|
| 48 |
``` cpp
|
| 49 |
vector<int> is{0,1,2,3,4,5,6,7,8,9};
|
| 50 |
+
for (int i : is | views::take(5))
|
| 51 |
+
cout << i << ' '; // prints 0 1 2 3 4
|
|
|
|
| 52 |
```
|
| 53 |
|
| 54 |
— *end example*]
|
| 55 |
|
| 56 |
#### Class template `take_view` <a id="range.take.view">[[range.take.view]]</a>
|
|
|
|
| 60 |
template<view V>
|
| 61 |
class take_view : public view_interface<take_view<V>> {
|
| 62 |
private:
|
| 63 |
V base_ = V(); // exposition only
|
| 64 |
range_difference_t<V> count_ = 0; // exposition only
|
| 65 |
+
|
| 66 |
// [range.take.sentinel], class template take_view::sentinel
|
| 67 |
+
template<bool> class sentinel; // exposition only
|
| 68 |
+
|
| 69 |
public:
|
| 70 |
+
take_view() requires default_initializable<V> = default;
|
| 71 |
+
constexpr explicit take_view(V base, range_difference_t<V> count);
|
| 72 |
|
| 73 |
constexpr V base() const & requires copy_constructible<V> { return base_; }
|
| 74 |
constexpr V base() && { return std::move(base_); }
|
| 75 |
|
| 76 |
constexpr auto begin() requires (!simple-view<V>) {
|
| 77 |
if constexpr (sized_range<V>) {
|
| 78 |
+
if constexpr (random_access_range<V>) {
|
| 79 |
return ranges::begin(base_);
|
| 80 |
+
} else {
|
| 81 |
+
auto sz = range_difference_t<V>(size());
|
| 82 |
+
return counted_iterator(ranges::begin(base_), sz);
|
| 83 |
+
}
|
| 84 |
+
} else if constexpr (sized_sentinel_for<sentinel_t<V>, iterator_t<V>>) {
|
| 85 |
+
auto it = ranges::begin(base_);
|
| 86 |
+
auto sz = std::min(count_, ranges::end(base_) - it);
|
| 87 |
+
return counted_iterator(std::move(it), sz);
|
| 88 |
+
} else {
|
| 89 |
+
return counted_iterator(ranges::begin(base_), count_);
|
| 90 |
}
|
|
|
|
|
|
|
| 91 |
}
|
| 92 |
|
| 93 |
constexpr auto begin() const requires range<const V> {
|
| 94 |
if constexpr (sized_range<const V>) {
|
| 95 |
+
if constexpr (random_access_range<const V>) {
|
| 96 |
return ranges::begin(base_);
|
| 97 |
+
} else {
|
| 98 |
+
auto sz = range_difference_t<const V>(size());
|
| 99 |
+
return counted_iterator(ranges::begin(base_), sz);
|
| 100 |
+
}
|
| 101 |
+
} else if constexpr (sized_sentinel_for<sentinel_t<const V>, iterator_t<const V>>) {
|
| 102 |
+
auto it = ranges::begin(base_);
|
| 103 |
+
auto sz = std::min(count_, ranges::end(base_) - it);
|
| 104 |
+
return counted_iterator(std::move(it), sz);
|
| 105 |
+
} else {
|
| 106 |
+
return counted_iterator(ranges::begin(base_), count_);
|
| 107 |
}
|
|
|
|
|
|
|
| 108 |
}
|
| 109 |
|
| 110 |
constexpr auto end() requires (!simple-view<V>) {
|
| 111 |
if constexpr (sized_range<V>) {
|
| 112 |
if constexpr (random_access_range<V>)
|
| 113 |
+
return ranges::begin(base_) + range_difference_t<V>(size());
|
| 114 |
else
|
| 115 |
return default_sentinel;
|
| 116 |
+
} else if constexpr (sized_sentinel_for<sentinel_t<V>, iterator_t<V>>) {
|
| 117 |
+
return default_sentinel;
|
| 118 |
+
} else {
|
| 119 |
return sentinel<false>{ranges::end(base_)};
|
| 120 |
}
|
| 121 |
+
}
|
| 122 |
|
| 123 |
constexpr auto end() const requires range<const V> {
|
| 124 |
if constexpr (sized_range<const V>) {
|
| 125 |
if constexpr (random_access_range<const V>)
|
| 126 |
+
return ranges::begin(base_) + range_difference_t<const V>(size());
|
| 127 |
else
|
| 128 |
return default_sentinel;
|
| 129 |
+
} else if constexpr (sized_sentinel_for<sentinel_t<const V>, iterator_t<const V>>) {
|
| 130 |
+
return default_sentinel;
|
| 131 |
+
} else {
|
| 132 |
return sentinel<true>{ranges::end(base_)};
|
| 133 |
}
|
| 134 |
+
}
|
| 135 |
|
| 136 |
constexpr auto size() requires sized_range<V> {
|
| 137 |
auto n = ranges::size(base_);
|
| 138 |
return ranges::min(n, static_cast<decltype(n)>(count_));
|
| 139 |
}
|
|
|
|
| 142 |
auto n = ranges::size(base_);
|
| 143 |
return ranges::min(n, static_cast<decltype(n)>(count_));
|
| 144 |
}
|
| 145 |
};
|
| 146 |
|
| 147 |
+
template<class R>
|
| 148 |
take_view(R&&, range_difference_t<R>)
|
| 149 |
-> take_view<views::all_t<R>>;
|
| 150 |
}
|
| 151 |
```
|
| 152 |
|
| 153 |
``` cpp
|
| 154 |
+
constexpr explicit take_view(V base, range_difference_t<V> count);
|
| 155 |
```
|
| 156 |
|
| 157 |
+
*Preconditions:* `count >= 0` is `true`.
|
| 158 |
+
|
| 159 |
*Effects:* Initializes *base\_* with `std::move(base)` and *count\_*
|
| 160 |
with `count`.
|
| 161 |
|
| 162 |
#### Class template `take_view::sentinel` <a id="range.take.sentinel">[[range.take.sentinel]]</a>
|
| 163 |
|
|
|
|
| 165 |
namespace std::ranges {
|
| 166 |
template<view V>
|
| 167 |
template<bool Const>
|
| 168 |
class take_view<V>::sentinel {
|
| 169 |
private:
|
| 170 |
+
using Base = maybe-const<Const, V>; // exposition only
|
| 171 |
+
template<bool OtherConst>
|
| 172 |
+
using CI = counted_iterator<iterator_t<maybe-const<OtherConst, V>>>; // exposition only
|
| 173 |
sentinel_t<Base> end_ = sentinel_t<Base>(); // exposition only
|
| 174 |
+
|
| 175 |
public:
|
| 176 |
sentinel() = default;
|
| 177 |
constexpr explicit sentinel(sentinel_t<Base> end);
|
| 178 |
constexpr sentinel(sentinel<!Const> s)
|
| 179 |
requires Const && convertible_to<sentinel_t<V>, sentinel_t<Base>>;
|
| 180 |
|
| 181 |
constexpr sentinel_t<Base> base() const;
|
| 182 |
|
| 183 |
+
friend constexpr bool operator==(const CI<Const>& y, const sentinel& x);
|
| 184 |
+
|
| 185 |
+
template<bool OtherConst = !Const>
|
| 186 |
+
requires sentinel_for<sentinel_t<Base>, iterator_t<maybe-const<OtherConst, V>>>
|
| 187 |
+
friend constexpr bool operator==(const CI<OtherConst>& y, const sentinel& x);
|
| 188 |
};
|
| 189 |
}
|
| 190 |
```
|
| 191 |
|
| 192 |
``` cpp
|
|
|
|
| 207 |
```
|
| 208 |
|
| 209 |
*Effects:* Equivalent to: `return `*`end_`*`;`
|
| 210 |
|
| 211 |
``` cpp
|
| 212 |
+
friend constexpr bool operator==(const CI<Const>& y, const sentinel& x);
|
| 213 |
+
|
| 214 |
+
template<bool OtherConst = !Const>
|
| 215 |
+
requires sentinel_for<sentinel_t<Base>, iterator_t<maybe-const<OtherConst, V>>>
|
| 216 |
+
friend constexpr bool operator==(const CI<OtherConst>& y, const sentinel& x);
|
| 217 |
```
|
| 218 |
|
| 219 |
*Effects:* Equivalent to:
|
| 220 |
`return y.count() == 0 || y.base() == x.`*`end_`*`;`
|
| 221 |
|