From Jason Turner

[view.interface]

Diff to HTML by rtfpessoa

Files changed (1) hide show
  1. tmp/tmp43z2im40/{from.md → to.md} +30 -8
tmp/tmp43z2im40/{from.md → to.md} RENAMED
@@ -1,31 +1,53 @@
1
  ### View interface <a id="view.interface">[[view.interface]]</a>
2
 
3
- The class template `view_interface` is a helper for defining `view`-like
 
 
4
  types that offer a container-like interface. It is parameterized with
5
  the type that is derived from it.
6
 
7
  ``` cpp
8
  namespace std::ranges {
9
  template<class D>
10
  requires is_class_v<D> && same_as<D, remove_cv_t<D>>
11
- class view_interface : public view_base {
12
  private:
13
  constexpr D& derived() noexcept { // exposition only
14
  return static_cast<D&>(*this);
15
  }
16
  constexpr const D& derived() const noexcept { // exposition only
17
  return static_cast<const D&>(*this);
18
  }
 
19
  public:
20
- constexpr bool empty() requires forward_range<D> {
 
 
 
21
  return ranges::begin(derived()) == ranges::end(derived());
22
  }
23
- constexpr bool empty() const requires forward_range<const D> {
 
 
 
24
  return ranges::begin(derived()) == ranges::end(derived());
25
  }
26
 
 
 
 
 
 
 
 
 
 
 
 
 
 
27
  constexpr explicit operator bool()
28
  requires requires { ranges::empty(derived()); } {
29
  return !ranges::empty(derived());
30
  }
31
  constexpr explicit operator bool() const
@@ -41,15 +63,15 @@ namespace std::ranges {
41
  return to_address(ranges::begin(derived()));
42
  }
43
 
44
  constexpr auto size() requires forward_range<D> &&
45
  sized_sentinel_for<sentinel_t<D>, iterator_t<D>> {
46
- return ranges::end(derived()) - ranges::begin(derived());
47
  }
48
  constexpr auto size() const requires forward_range<const D> &&
49
  sized_sentinel_for<sentinel_t<const D>, iterator_t<const D>> {
50
- return ranges::end(derived()) - ranges::begin(derived());
51
  }
52
 
53
  constexpr decltype(auto) front() requires forward_range<D>;
54
  constexpr decltype(auto) front() const requires forward_range<const D>;
55
 
@@ -80,20 +102,20 @@ shall be complete, and model both `derived_from<view_interface<D>>` and
80
  ``` cpp
81
  constexpr decltype(auto) front() requires forward_range<D>;
82
  constexpr decltype(auto) front() const requires forward_range<const D>;
83
  ```
84
 
85
- *Preconditions:* `!empty()`.
86
 
87
  *Effects:* Equivalent to: `return *ranges::begin(`*`derived`*`());`
88
 
89
  ``` cpp
90
  constexpr decltype(auto) back() requires bidirectional_range<D> && common_range<D>;
91
  constexpr decltype(auto) back() const
92
  requires bidirectional_range<const D> && common_range<const D>;
93
  ```
94
 
95
- *Preconditions:* `!empty()`.
96
 
97
  *Effects:* Equivalent to:
98
  `return *ranges::prev(ranges::end(`*`derived`*`()));`
99
 
 
1
  ### View interface <a id="view.interface">[[view.interface]]</a>
2
 
3
+ #### General <a id="view.interface.general">[[view.interface.general]]</a>
4
+
5
+ The class template `view_interface` is a helper for defining view-like
6
  types that offer a container-like interface. It is parameterized with
7
  the type that is derived from it.
8
 
9
  ``` cpp
10
  namespace std::ranges {
11
  template<class D>
12
  requires is_class_v<D> && same_as<D, remove_cv_t<D>>
13
+ class view_interface {
14
  private:
15
  constexpr D& derived() noexcept { // exposition only
16
  return static_cast<D&>(*this);
17
  }
18
  constexpr const D& derived() const noexcept { // exposition only
19
  return static_cast<const D&>(*this);
20
  }
21
+
22
  public:
23
+ constexpr bool empty() requires sized_range<D> || forward_range<D> {
24
+ if constexpr (sized_range<D>)
25
+ return ranges::size(derived()) == 0;
26
+ else
27
  return ranges::begin(derived()) == ranges::end(derived());
28
  }
29
+ constexpr bool empty() const requires sized_range<const D> || forward_range<const D> {
30
+ if constexpr (sized_range<const D>)
31
+ return ranges::size(derived()) == 0;
32
+ else
33
  return ranges::begin(derived()) == ranges::end(derived());
34
  }
35
 
36
+ constexpr auto cbegin() requires input_range<D> {
37
+ return ranges::cbegin(derived());
38
+ }
39
+ constexpr auto cbegin() const requires input_range<const D> {
40
+ return ranges::cbegin(derived());
41
+ }
42
+ constexpr auto cend() requires input_range<D> {
43
+ return ranges::cend(derived());
44
+ }
45
+ constexpr auto cend() const requires input_range<const D> {
46
+ return ranges::cend(derived());
47
+ }
48
+
49
  constexpr explicit operator bool()
50
  requires requires { ranges::empty(derived()); } {
51
  return !ranges::empty(derived());
52
  }
53
  constexpr explicit operator bool() const
 
63
  return to_address(ranges::begin(derived()));
64
  }
65
 
66
  constexpr auto size() requires forward_range<D> &&
67
  sized_sentinel_for<sentinel_t<D>, iterator_t<D>> {
68
+ return to-unsigned-like(ranges::end(derived()) - ranges::begin(derived()));
69
  }
70
  constexpr auto size() const requires forward_range<const D> &&
71
  sized_sentinel_for<sentinel_t<const D>, iterator_t<const D>> {
72
+ return to-unsigned-like(ranges::end(derived()) - ranges::begin(derived()));
73
  }
74
 
75
  constexpr decltype(auto) front() requires forward_range<D>;
76
  constexpr decltype(auto) front() const requires forward_range<const D>;
77
 
 
102
  ``` cpp
103
  constexpr decltype(auto) front() requires forward_range<D>;
104
  constexpr decltype(auto) front() const requires forward_range<const D>;
105
  ```
106
 
107
+ *Preconditions:* `!empty()` is `true`.
108
 
109
  *Effects:* Equivalent to: `return *ranges::begin(`*`derived`*`());`
110
 
111
  ``` cpp
112
  constexpr decltype(auto) back() requires bidirectional_range<D> && common_range<D>;
113
  constexpr decltype(auto) back() const
114
  requires bidirectional_range<const D> && common_range<const D>;
115
  ```
116
 
117
+ *Preconditions:* `!empty()` is `true`.
118
 
119
  *Effects:* Equivalent to:
120
  `return *ranges::prev(ranges::end(`*`derived`*`()));`
121