blob: 5d455922f639a27b3f25fd11a2fcdf0ebfcc1ffa [file] [log] [blame]
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -07001// Protocol Buffers - Google's data interchange format
2// Copyright 2023 Google LLC. All rights reserved.
3//
4// Use of this source code is governed by a BSD-style
5// license that can be found in the LICENSE file or at
6// https://developers.google.com/open-source/licenses/bsd
7
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -08008use std::fmt::{self, Debug};
9use std::iter;
Protobuf Team Bot14dd8e92023-12-15 11:05:56 -080010use std::iter::FusedIterator;
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070011/// Repeated scalar fields are implemented around the runtime-specific
12/// `RepeatedField` struct. `RepeatedField` stores an opaque pointer to the
13/// runtime-specific representation of a repeated scalar (`upb_Array*` on upb,
14/// and `RepeatedField<T>*` on cpp).
15use std::marker::PhantomData;
16
17use crate::{
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -070018 IntoProxied, Mut, MutProxied, MutProxy, Proxied, View, ViewProxy,
Protobuf Team Bot2678e102024-04-12 13:50:28 -070019 __internal::Private,
20 __runtime::{InnerRepeated, InnerRepeatedMut, RawRepeatedField},
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070021};
22
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080023/// Views the elements in a `repeated` field of `T`.
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070024#[repr(transparent)]
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070025pub struct RepeatedView<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080026 // This does not need to carry an arena in upb, so it can be just the raw repeated field
27 raw: RawRepeatedField,
28 _phantom: PhantomData<&'msg T>,
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070029}
30
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070031impl<'msg, T> Copy for RepeatedView<'msg, T> {}
32impl<'msg, T> Clone for RepeatedView<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080033 fn clone(&self) -> Self {
34 *self
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070035 }
36}
37
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070038unsafe impl<'msg, T> Sync for RepeatedView<'msg, T> {}
39unsafe impl<'msg, T> Send for RepeatedView<'msg, T> {}
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070040
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070041impl<'msg, T> Debug for RepeatedView<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080042 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
43 f.debug_struct("RepeatedView").field("raw", &self.raw).finish()
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070044 }
45}
46
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080047/// Mutates the elements in a `repeated` field of `T`.
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070048pub struct RepeatedMut<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080049 pub(crate) inner: InnerRepeatedMut<'msg>,
50 _phantom: PhantomData<&'msg mut T>,
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070051}
52
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070053unsafe impl<'msg, T> Sync for RepeatedMut<'msg, T> {}
Kevin King65cdac42023-10-23 14:50:42 -070054
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070055impl<'msg, T> Debug for RepeatedMut<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080056 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -080057 f.debug_struct("RepeatedMut").field("raw", &self.inner.raw).finish()
Protobuf Team Bote1bb7d62023-10-17 14:15:37 -070058 }
59}
60
Alyssa Haroldsen3657e052024-02-05 12:51:41 -080061#[doc(hidden)]
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070062impl<'msg, T> RepeatedView<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080063 #[doc(hidden)]
Derek Benson904266d2024-05-13 07:16:57 -070064 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080065 pub fn as_raw(&self, _private: Private) -> RawRepeatedField {
66 self.raw
67 }
68
69 /// # Safety
70 /// - `inner` must be valid to read from for `'msg`
71 #[doc(hidden)]
Derek Benson904266d2024-05-13 07:16:57 -070072 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080073 pub unsafe fn from_raw(_private: Private, raw: RawRepeatedField) -> Self {
74 Self { raw, _phantom: PhantomData }
75 }
Alyssa Haroldsen3657e052024-02-05 12:51:41 -080076}
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080077
Alyssa Haroldsen3657e052024-02-05 12:51:41 -080078impl<'msg, T> RepeatedView<'msg, T>
79where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -070080 T: ProxiedInRepeated + 'msg,
Alyssa Haroldsen3657e052024-02-05 12:51:41 -080081{
Alyssa Haroldsenfcf0d012023-12-18 10:13:01 -080082 /// Gets the length of the repeated field.
Derek Benson904266d2024-05-13 07:16:57 -070083 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080084 pub fn len(&self) -> usize {
85 T::repeated_len(*self)
86 }
Alyssa Haroldsenfcf0d012023-12-18 10:13:01 -080087
88 /// Returns true if the repeated field has no values.
Derek Benson904266d2024-05-13 07:16:57 -070089 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080090 pub fn is_empty(&self) -> bool {
91 self.len() == 0
92 }
Alyssa Haroldsenfcf0d012023-12-18 10:13:01 -080093
94 /// Gets the value at `index`.
95 ///
96 /// Returns `None` if `index > len`.
Derek Benson904266d2024-05-13 07:16:57 -070097 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -080098 pub fn get(self, index: usize) -> Option<View<'msg, T>> {
99 if index >= self.len() {
100 return None;
101 }
102 // SAFETY: `index` has been checked to be in-bounds
Alyssa Haroldsenfcf0d012023-12-18 10:13:01 -0800103 Some(unsafe { self.get_unchecked(index) })
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800104 }
Alyssa Haroldsenfcf0d012023-12-18 10:13:01 -0800105
106 /// Gets the value at `index` without bounds-checking.
107 ///
108 /// # Safety
109 /// Undefined behavior if `index >= len`
Derek Benson904266d2024-05-13 07:16:57 -0700110 #[inline]
Alyssa Haroldsenfcf0d012023-12-18 10:13:01 -0800111 pub unsafe fn get_unchecked(self, index: usize) -> View<'msg, T> {
112 // SAFETY: in-bounds as promised
113 unsafe { T::repeated_get_unchecked(self, index) }
114 }
115
116 /// Iterates over the values in the repeated field.
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800117 pub fn iter(self) -> RepeatedIter<'msg, T> {
118 self.into_iter()
119 }
120}
121
Alyssa Haroldsen3657e052024-02-05 12:51:41 -0800122#[doc(hidden)]
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700123impl<'msg, T> RepeatedMut<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800124 /// # Safety
125 /// - `inner` must be valid to read and write from for `'msg`
126 /// - There must be no aliasing references or mutations on the same
127 /// underlying object.
128 #[doc(hidden)]
Derek Benson904266d2024-05-13 07:16:57 -0700129 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800130 pub unsafe fn from_inner(_private: Private, inner: InnerRepeatedMut<'msg>) -> Self {
131 Self { inner, _phantom: PhantomData }
132 }
133
134 #[doc(hidden)]
Derek Benson904266d2024-05-13 07:16:57 -0700135 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800136 pub fn as_raw(&mut self, _private: Private) -> RawRepeatedField {
137 self.inner.raw
138 }
Alyssa Haroldsen3657e052024-02-05 12:51:41 -0800139}
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800140
Alyssa Haroldsen3657e052024-02-05 12:51:41 -0800141impl<'msg, T> RepeatedMut<'msg, T>
142where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700143 T: ProxiedInRepeated + 'msg,
Alyssa Haroldsen3657e052024-02-05 12:51:41 -0800144{
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -0800145 /// Gets the length of the repeated field.
Derek Benson904266d2024-05-13 07:16:57 -0700146 #[inline]
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -0800147 pub fn len(&self) -> usize {
148 self.as_view().len()
149 }
150
151 /// Returns true if the repeated field has no values.
Derek Benson904266d2024-05-13 07:16:57 -0700152 #[inline]
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -0800153 pub fn is_empty(&self) -> bool {
154 self.len() == 0
155 }
156
157 /// Gets the value at `index`.
158 ///
159 /// Returns `None` if `index > len`.
Derek Benson904266d2024-05-13 07:16:57 -0700160 #[inline]
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -0800161 pub fn get(&self, index: usize) -> Option<View<T>> {
162 self.as_view().get(index)
163 }
164
165 /// Gets the value at `index` without bounds-checking.
166 ///
167 /// # Safety
168 /// Undefined behavior if `index >= len`
Derek Benson904266d2024-05-13 07:16:57 -0700169 #[inline]
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -0800170 pub unsafe fn get_unchecked(&self, index: usize) -> View<T> {
171 // SAFETY: in-bounds as promised
172 unsafe { self.as_view().get_unchecked(index) }
173 }
174
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800175 /// Appends `val` to the end of the repeated field.
Derek Benson904266d2024-05-13 07:16:57 -0700176 #[inline]
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700177 pub fn push(&mut self, val: impl IntoProxied<T>) {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800178 T::repeated_push(self.as_mut(), val);
179 }
180
181 /// Sets the value at `index` to the value `val`.
182 ///
183 /// # Panics
184 /// Panics if `index >= len`
Derek Benson904266d2024-05-13 07:16:57 -0700185 #[inline]
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700186 pub fn set(&mut self, index: usize, val: impl IntoProxied<T>) {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800187 let len = self.len();
188 if index >= len {
189 panic!("index {index} >= repeated len {len}");
190 }
Alyssa Haroldsenfcf0d012023-12-18 10:13:01 -0800191 unsafe { self.set_unchecked(index, val) }
192 }
193
194 /// Sets the value at `index` to the value `val`.
195 ///
196 /// # Safety
197 /// Undefined behavior if `index >= len`
Derek Benson904266d2024-05-13 07:16:57 -0700198 #[inline]
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700199 pub unsafe fn set_unchecked(&mut self, index: usize, val: impl IntoProxied<T>) {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800200 unsafe { T::repeated_set_unchecked(self.as_mut(), index, val) }
201 }
202
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -0800203 /// Iterates over the values in the repeated field.
204 pub fn iter(&self) -> RepeatedIter<T> {
205 self.as_view().into_iter()
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800206 }
207
208 /// Copies from the `src` repeated field into this one.
209 ///
210 /// Also provided by [`MutProxy::set`].
211 pub fn copy_from(&mut self, src: RepeatedView<'_, T>) {
212 T::repeated_copy_from(src, self.as_mut())
213 }
Alyssa Haroldsenf51182b2023-12-14 14:07:40 -0800214
215 /// Clears the repeated field.
216 pub fn clear(&mut self) {
217 T::repeated_clear(self.as_mut())
218 }
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800219}
220
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700221impl<T> Repeated<T>
222where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700223 T: ProxiedInRepeated,
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700224{
225 pub fn as_view(&self) -> View<Repeated<T>> {
226 RepeatedView { raw: self.inner.raw(), _phantom: PhantomData }
227 }
228
229 #[doc(hidden)]
230 pub fn inner(&self, _private: Private) -> &InnerRepeated {
231 &self.inner
232 }
233}
234
235impl<T> IntoProxied<Repeated<T>> for Repeated<T>
236where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700237 T: ProxiedInRepeated,
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700238{
Marcel Hlopkofe696392024-06-12 05:26:09 -0700239 fn into_proxied(self, _private: Private) -> Repeated<T> {
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700240 self
241 }
242}
243
244impl<'msg, T> IntoProxied<Repeated<T>> for RepeatedView<'msg, T>
245where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700246 T: 'msg + ProxiedInRepeated,
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700247{
Marcel Hlopkofe696392024-06-12 05:26:09 -0700248 fn into_proxied(self, _private: Private) -> Repeated<T> {
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700249 let mut repeated: Repeated<T> = Repeated::new();
250 T::repeated_copy_from(self, repeated.as_mut());
251 repeated
252 }
253}
254
255impl<'msg, T> IntoProxied<Repeated<T>> for RepeatedMut<'msg, T>
256where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700257 T: 'msg + ProxiedInRepeated,
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700258{
Marcel Hlopkofe696392024-06-12 05:26:09 -0700259 fn into_proxied(self, _private: Private) -> Repeated<T> {
260 IntoProxied::into_proxied(self.as_view(), _private)
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700261 }
262}
263
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800264/// Types that can appear in a `Repeated<T>`.
265///
266/// This trait is implemented by generated code to communicate how the proxied
267/// type can be manipulated for a repeated field.
268///
269/// Scalars and messages implement `ProxiedInRepeated`.
270///
271/// # Safety
272/// - It must be sound to call `*_unchecked*(x)` with an `index` less than
273/// `repeated_len(x)`.
274pub unsafe trait ProxiedInRepeated: Proxied {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800275 /// Constructs a new owned `Repeated` field.
276 #[doc(hidden)]
277 fn repeated_new(_private: Private) -> Repeated<Self> {
278 unimplemented!("not required")
279 }
280
Alyssa Haroldsenf51182b2023-12-14 14:07:40 -0800281 /// Frees the repeated field in-place, for use in `Drop`.
282 ///
283 /// # Safety
284 /// - After `repeated_free`, no other methods on the input are safe to call.
285 #[doc(hidden)]
286 unsafe fn repeated_free(_private: Private, _repeated: &mut Repeated<Self>) {
287 unimplemented!("not required")
288 }
289
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800290 /// Gets the length of the repeated field.
291 fn repeated_len(repeated: View<Repeated<Self>>) -> usize;
292
293 /// Appends a new element to the end of the repeated field.
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700294 fn repeated_push(repeated: Mut<Repeated<Self>>, val: impl IntoProxied<Self>);
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800295
Alyssa Haroldsenf51182b2023-12-14 14:07:40 -0800296 /// Clears the repeated field of elements.
297 fn repeated_clear(repeated: Mut<Repeated<Self>>);
298
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800299 /// # Safety
300 /// `index` must be less than `Self::repeated_len(repeated)`
301 unsafe fn repeated_get_unchecked(repeated: View<Repeated<Self>>, index: usize) -> View<Self>;
302
303 /// # Safety
304 /// `index` must be less than `Self::repeated_len(repeated)`
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700305 unsafe fn repeated_set_unchecked(
306 repeated: Mut<Repeated<Self>>,
307 index: usize,
308 val: impl IntoProxied<Self>,
309 );
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800310
311 /// Copies the values in the `src` repeated field into `dest`.
312 fn repeated_copy_from(src: View<Repeated<Self>>, dest: Mut<Repeated<Self>>);
Derek Bensonf2d8c2b2024-05-13 05:48:10 -0700313
314 /// Ensures that the repeated field has enough space allocated to insert at
315 /// least `additional` values without an allocation.
316 fn repeated_reserve(repeated: Mut<Repeated<Self>>, additional: usize);
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800317}
318
319/// An iterator over the values inside of a [`View<Repeated<T>>`](RepeatedView).
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700320pub struct RepeatedIter<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800321 view: RepeatedView<'msg, T>,
322 current_index: usize,
323}
324
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700325impl<'msg, T> Debug for RepeatedIter<'msg, T> {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800326 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
327 f.debug_struct("RepeatedIter")
328 .field("view", &self.view)
329 .field("current_index", &self.current_index)
330 .finish()
331 }
332}
333
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800334/// A `repeated` field of `T`, used as the owned target for `Proxied`.
335///
336/// Users will generally write [`View<Repeated<T>>`](RepeatedView) or
337/// [`Mut<Repeated<T>>`](RepeatedMut) to access the repeated elements
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700338pub struct Repeated<T: ProxiedInRepeated> {
Jakob Buchgraberb6e0a482024-05-06 05:16:05 -0700339 pub(crate) inner: InnerRepeated,
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800340 _phantom: PhantomData<T>,
341}
342
Jakob Buchgraber3c9978d2024-06-04 01:27:57 -0700343// SAFETY: `Repeated` is Sync because it does not implement interior mutability.
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700344unsafe impl<T: ProxiedInRepeated> Sync for Repeated<T> {}
Jakob Buchgraber3c9978d2024-06-04 01:27:57 -0700345
346// SAFETY: `Repeated` is Send because it's not bound to a specific thread e.g.
347// it does not use thread-local data or similar.
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700348unsafe impl<T: ProxiedInRepeated> Send for Repeated<T> {}
Jakob Buchgraber3c9978d2024-06-04 01:27:57 -0700349
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700350impl<T: ProxiedInRepeated> Repeated<T> {
Jakob Buchgraberad5e55a2024-03-12 05:45:32 -0700351 pub fn new() -> Self {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800352 T::repeated_new(Private)
353 }
354
Protobuf Team Bot9ff062c2024-03-12 04:48:15 -0700355 pub(crate) fn from_inner(inner: InnerRepeated) -> Self {
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800356 Self { inner, _phantom: PhantomData }
357 }
358
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800359 pub(crate) fn as_mut(&mut self) -> RepeatedMut<'_, T> {
Protobuf Team Bot9ff062c2024-03-12 04:48:15 -0700360 RepeatedMut { inner: self.inner.as_mut(), _phantom: PhantomData }
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800361 }
362}
363
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700364impl<T: ProxiedInRepeated> Default for Repeated<T> {
Jakob Buchgraberad5e55a2024-03-12 05:45:32 -0700365 fn default() -> Self {
366 Repeated::new()
367 }
368}
369
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700370impl<T: ProxiedInRepeated> Drop for Repeated<T> {
Alyssa Haroldsenf51182b2023-12-14 14:07:40 -0800371 fn drop(&mut self) {
372 // SAFETY: only called once
373 unsafe { T::repeated_free(Private, self) }
374 }
375}
376
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800377impl<T> Proxied for Repeated<T>
378where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700379 T: ProxiedInRepeated,
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800380{
381 type View<'msg> = RepeatedView<'msg, T> where Repeated<T>: 'msg;
Jakob Buchgraber1a7ce612024-04-24 06:21:54 -0700382}
383
384impl<T> MutProxied for Repeated<T>
385where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700386 T: ProxiedInRepeated,
Jakob Buchgraber1a7ce612024-04-24 06:21:54 -0700387{
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800388 type Mut<'msg> = RepeatedMut<'msg, T> where Repeated<T>: 'msg;
389}
390
391impl<'msg, T> ViewProxy<'msg> for RepeatedView<'msg, T>
392where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700393 T: ProxiedInRepeated + 'msg,
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800394{
395 type Proxied = Repeated<T>;
396
Derek Benson904266d2024-05-13 07:16:57 -0700397 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800398 fn as_view(&self) -> View<'_, Self::Proxied> {
399 *self
400 }
401
Derek Benson904266d2024-05-13 07:16:57 -0700402 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800403 fn into_view<'shorter>(self) -> View<'shorter, Self::Proxied>
404 where
405 'msg: 'shorter,
406 {
407 RepeatedView { raw: self.raw, _phantom: PhantomData }
408 }
409}
410
411impl<'msg, T> ViewProxy<'msg> for RepeatedMut<'msg, T>
412where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700413 T: ProxiedInRepeated + 'msg,
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800414{
415 type Proxied = Repeated<T>;
416
Derek Benson904266d2024-05-13 07:16:57 -0700417 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800418 fn as_view(&self) -> View<'_, Self::Proxied> {
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -0800419 RepeatedView { raw: self.inner.raw, _phantom: PhantomData }
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800420 }
421
Derek Benson904266d2024-05-13 07:16:57 -0700422 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800423 fn into_view<'shorter>(self) -> View<'shorter, Self::Proxied>
424 where
425 'msg: 'shorter,
426 {
Alyssa Haroldsenb6ea6f92024-01-17 16:50:36 -0800427 RepeatedView { raw: self.inner.raw, _phantom: PhantomData }
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800428 }
429}
430
431impl<'msg, T> MutProxy<'msg> for RepeatedMut<'msg, T>
432where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700433 T: ProxiedInRepeated + 'msg,
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800434{
Derek Benson904266d2024-05-13 07:16:57 -0700435 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800436 fn as_mut(&mut self) -> Mut<'_, Self::Proxied> {
437 RepeatedMut { inner: self.inner, _phantom: PhantomData }
438 }
439
Derek Benson904266d2024-05-13 07:16:57 -0700440 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800441 fn into_mut<'shorter>(self) -> Mut<'shorter, Self::Proxied>
442 where
443 'msg: 'shorter,
444 {
445 RepeatedMut { inner: self.inner, _phantom: PhantomData }
446 }
447}
448
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800449impl<'msg, T> iter::Iterator for RepeatedIter<'msg, T>
450where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700451 T: ProxiedInRepeated + 'msg,
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800452{
453 type Item = View<'msg, T>;
454
Derek Benson904266d2024-05-13 07:16:57 -0700455 #[inline]
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800456 fn next(&mut self) -> Option<Self::Item> {
457 let val = self.view.get(self.current_index);
458 if val.is_some() {
459 self.current_index += 1;
460 }
461 val
462 }
Alyssa Haroldsen39850822024-02-06 11:06:14 -0800463
464 fn size_hint(&self) -> (usize, Option<usize>) {
465 let len = self.len();
466 (len, Some(len))
467 }
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800468}
469
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700470impl<'msg, T: ProxiedInRepeated> ExactSizeIterator for RepeatedIter<'msg, T> {
Protobuf Team Bot14dd8e92023-12-15 11:05:56 -0800471 fn len(&self) -> usize {
Alyssa Haroldsen39850822024-02-06 11:06:14 -0800472 self.view.len() - self.current_index
Protobuf Team Bot14dd8e92023-12-15 11:05:56 -0800473 }
474}
475
Alyssa Haroldsen39850822024-02-06 11:06:14 -0800476// TODO: impl DoubleEndedIterator
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700477impl<'msg, T: ProxiedInRepeated> FusedIterator for RepeatedIter<'msg, T> {}
Protobuf Team Bot14dd8e92023-12-15 11:05:56 -0800478
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800479impl<'msg, T> iter::IntoIterator for RepeatedView<'msg, T>
480where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700481 T: ProxiedInRepeated + 'msg,
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800482{
483 type Item = View<'msg, T>;
484 type IntoIter = RepeatedIter<'msg, T>;
485
486 fn into_iter(self) -> Self::IntoIter {
487 RepeatedIter { view: self, current_index: 0 }
488 }
489}
490
Alyssa Haroldsene16dd472024-01-17 14:02:06 -0800491impl<'msg, T> iter::IntoIterator for &'_ RepeatedView<'msg, T>
492where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700493 T: ProxiedInRepeated + 'msg,
Alyssa Haroldsene16dd472024-01-17 14:02:06 -0800494{
495 type Item = View<'msg, T>;
496 type IntoIter = RepeatedIter<'msg, T>;
497
498 fn into_iter(self) -> Self::IntoIter {
499 RepeatedIter { view: *self, current_index: 0 }
500 }
501}
502
503impl<'borrow, T> iter::IntoIterator for &'borrow RepeatedMut<'_, T>
504where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700505 T: ProxiedInRepeated + 'borrow,
Alyssa Haroldsene16dd472024-01-17 14:02:06 -0800506{
507 type Item = View<'borrow, T>;
508 type IntoIter = RepeatedIter<'borrow, T>;
509
510 fn into_iter(self) -> Self::IntoIter {
511 RepeatedIter { view: self.as_view(), current_index: 0 }
512 }
513}
514
Protobuf Team Bot7f6a0ba2024-03-29 10:26:49 -0700515impl<'msg, 'view, T, ViewT> Extend<ViewT> for RepeatedMut<'msg, T>
516where
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700517 T: ProxiedInRepeated + 'view,
518 ViewT: IntoProxied<T>,
Protobuf Team Bot7f6a0ba2024-03-29 10:26:49 -0700519{
520 fn extend<I: IntoIterator<Item = ViewT>>(&mut self, iter: I) {
Derek Bensonf2d8c2b2024-05-13 05:48:10 -0700521 let iter = iter.into_iter();
522 T::repeated_reserve(self.as_mut(), iter.size_hint().0);
Protobuf Team Bot7f6a0ba2024-03-29 10:26:49 -0700523 for item in iter {
Jakob Buchgraber0d6e9792024-07-09 04:44:21 -0700524 self.push(item);
Protobuf Team Bot7f6a0ba2024-03-29 10:26:49 -0700525 }
526 }
527}
528
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800529#[cfg(test)]
530mod tests {
531 use super::*;
532 use googletest::prelude::*;
533
534 #[test]
535 fn test_primitive_repeated() {
536 macro_rules! primitive_repeated_tests {
537 ($($t:ty => [$($vals:expr),* $(,)?]),* $(,)?) => {
538 $({
539 // Constructs a new, owned, `Repeated`, only used for tests.
540 let mut r = Repeated::<$t>::new();
541 let mut r = r.as_mut();
542 assert_that!(r.len(), eq(0));
543 assert!(r.iter().next().is_none(), "starts with empty iter");
544 assert!(r.iter().next().is_none(), "starts with empty mut iter");
545 assert!(r.is_empty(), "starts is_empty");
546
547 let mut expected_len = 0usize;
548 $(
549 let val: View<$t> = $vals;
550 r.push(val);
551 assert_that!(r.get(expected_len), eq(Some(val)));
552 expected_len += 1;
553 assert_that!(r.len(), eq(expected_len));
554
555 )*
Bastien Jacot-Guillarmod7b3682f2024-05-03 09:50:45 -0700556 assert_that!(r, elements_are![$(eq($vals)),*]);
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800557 r.set(0, <$t as Default>::default());
558 assert_that!(r.get(0).expect("elem 0"), eq(<$t as Default>::default()));
Alyssa Haroldsenf51182b2023-12-14 14:07:40 -0800559
560 r.clear();
561 assert!(r.is_empty(), "is_empty after clear");
562 assert!(r.iter().next().is_none(), "iter empty after clear");
563 assert!(r.into_iter().next().is_none(), "mut iter empty after clear");
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800564 })*
565 }
566 }
567 primitive_repeated_tests!(
568 u32 => [1,2,3],
569 i32 => [1,2],
570 f64 => [10.0, 0.1234f64],
571 bool => [false, true, true, false],
572 );
573 }
Protobuf Team Bot7f6a0ba2024-03-29 10:26:49 -0700574
575 #[test]
576 fn test_repeated_extend() {
577 let mut r = Repeated::<i32>::new();
Protobuf Team Bot063c1982024-04-02 06:48:42 -0700578
579 r.as_mut().extend([0; 0]);
580 assert_that!(r.as_mut().len(), eq(0));
581
Protobuf Team Bot7f6a0ba2024-03-29 10:26:49 -0700582 r.as_mut().extend([0, 1]);
Bastien Jacot-Guillarmod7b3682f2024-05-03 09:50:45 -0700583 assert_that!(r.as_mut(), elements_are![eq(0), eq(1)]);
Protobuf Team Bot7f6a0ba2024-03-29 10:26:49 -0700584 let mut x = Repeated::<i32>::new();
585 x.as_mut().extend([2, 3]);
586
587 r.as_mut().extend(&x.as_mut());
588
Bastien Jacot-Guillarmod7b3682f2024-05-03 09:50:45 -0700589 assert_that!(r.as_mut(), elements_are![eq(0), eq(1), eq(2), eq(3)]);
Protobuf Team Bot7f6a0ba2024-03-29 10:26:49 -0700590 }
Alyssa Haroldsen6ae76fd2023-12-14 11:44:00 -0800591}