cl_generic_vec/
lib.rs

1#![cfg_attr(not(any(doc, feature = "std")), no_std)]
2#![cfg_attr(
3    any(doc, feature = "nightly"),
4    feature(
5        trusted_len,
6        min_specialization,
7        exact_size_is_empty,
8        allocator_api,
9        alloc_layout_extra,
10        const_fn_trait_bound,
11        const_mut_refs,
12        doc_cfg,
13        ptr_metadata,
14    )
15)]
16#![cfg_attr(all(feature = "nightly", feature = "alloc"), feature(new_uninit))]
17#![cfg_attr(feature = "nightly", forbid(unsafe_op_in_unsafe_fn))]
18#![allow(unused_unsafe)]
19#![forbid(missing_docs, clippy::missing_safety_doc)]
20#![warn(clippy::pedantic)]
21#![allow(clippy::must_use_candidate, clippy::module_name_repetitions)]
22
23//! A vector that can store items anywhere: in slices, arrays, or the heap!
24//!
25//! [`GenericVec`] has complete parity with [`Vec`], and even provides some features
26//! that are only in `nightly` on `std` (like [`GenericVec::drain_filter`]), or a more permissive
27//! interface like [`GenericVec::retain`]. In fact, you can trivially convert a [`Vec`] to a
28//! [`HeapVec`] and back!
29//!
30//! This crate is `no_std` compatible, just turn off all default features.
31//!
32//! # Features
33//!
34//! * `std` (default) - enables you to use an allocator, and
35//! * `alloc` - enables you to use an allocator, for heap allocated storages
36//!     (like [`Vec`])
37//! * `nightly` - enables you to use the Allocator trait
38//!
39//! # Basic Usage
40//!
41//! ### [`SliceVec`]
42//!
43//! [`SliceVec`] stores an uninit slice buffer, and they store all of thier values in that buffer.
44//!
45//! ```rust
46//! use cl_generic_vec::{SliceVec, uninit_array};
47//!
48//! let mut uninit_buffer = uninit_array::<_, 16>();
49//! let mut slice_vec = unsafe { SliceVec::new(&mut uninit_buffer) };
50//!
51//! assert!(slice_vec.is_empty());
52//! slice_vec.push(10);
53//! assert_eq!(slice_vec, [10]);
54//! ```
55//!
56//! Of course if you try to push past a `*SliceVec`'s capacity
57//! (the length of the slice you passed in), then it will panic.
58//!
59//! ### [`ArrayVec`](type@ArrayVec)
60//!
61//! [`ArrayVec`](type@ArrayVec) is like the slice version, but since they own their data,
62//! they can be freely moved around, unconstrained. You can also create
63//! a new [`ArrayVec`](type@ArrayVec) without passing in an existing buffer,
64//! unlike the slice versions.
65//!
66//! ```rust
67//! use cl_generic_vec::ArrayVec;
68//!
69//! let mut array_vec = ArrayVec::<i32, 16>::new();
70//!
71//! array_vec.push(10);
72//! array_vec.push(20);
73//! array_vec.push(30);
74//!
75//! assert_eq!(array_vec, [10, 20, 30]);
76//! ```
77//!
78//! ## `alloc`
79//!
80//! A [`HeapVec`] is just [`Vec`], but built atop [`GenericVec`],
81//! meaning you get all the features of [`GenericVec`] for free! But this
82//! requries either the `alloc` or `std` feature to be enabled.
83//!
84//! ```rust
85//! use cl_generic_vec::{HeapVec, gvec};
86//! let mut vec: HeapVec<u32> = gvec![1, 2, 3, 4];
87//! assert_eq!(vec.capacity(), 4);
88//! vec.extend([5, 6, 7, 8]);
89//!
90//! assert_eq!(vec, [1, 2, 3, 4, 5, 6, 7, 8]);
91//!
92//! vec.try_push(5).expect_err("Tried to push past capacity!");
93//! ```
94//!
95//! ## `nightly`
96//!
97//! On `nightly`
98//! * a number of optimizations are enabled
99//! * some diagnostics become better
100//!
101//! Note on the documentation: if the feature exists on [`Vec`], then the documentation
102//! is either exactly the same as [`Vec`] or slightly adapted to better fit [`GenericVec`]
103//!
104//! Note on implementation: large parts of the implementation came straight from [`Vec`]
105//! so thanks for the amazing reference `std`!
106
107#[cfg(all(feature = "alloc", not(feature = "std")))]
108extern crate alloc as std;
109
110use core::{
111    mem::{ManuallyDrop, MaybeUninit},
112    ops::{Deref, DerefMut, RangeBounds},
113    ptr,
114};
115
116mod extension;
117mod impls;
118mod slice;
119
120pub mod iter;
121pub mod raw;
122
123use raw::{AllocError, AllocResult, Storage};
124
125#[doc(hidden)]
126pub use core;
127
128/// A type provided purely for simplicity.
129///
130/// [`GenericVec`] includes it's `T` type as a type parameter,
131/// even though it can be trivially inferred from the [`Storage::Item`] field.
132/// This is because it helps in generic contexts, the T type just gives the compiler
133/// a little nudge to be able to tell apart a `GenericVec<Item = u8>` from `GenericVec<Item = u16>`.
134pub type SimpleVec<S> = GenericVec<<S as Storage>::Item, S>;
135
136/// A heap backed vector with a growable capacity
137#[cfg(any(doc, all(feature = "alloc", feature = "nightly")))]
138#[cfg_attr(doc, doc(cfg(all(feature = "alloc", feature = "nightly"))))]
139pub type HeapVec<T, A = std::alloc::Global> = GenericVec<T, Box<[MaybeUninit<T>], A>>;
140
141/// A heap backed vector with a growable capacity
142#[cfg(all(not(doc), feature = "alloc", not(feature = "nightly")))]
143#[cfg_attr(doc, doc(cfg(feature = "alloc")))]
144pub type HeapVec<T> = GenericVec<T, Box<[MaybeUninit<T>]>>;
145
146/// An array backed vector backed by potentially uninitialized memory
147pub type ArrayVec<T, const N: usize> = GenericVec<T, [MaybeUninit<T>; N]>;
148/// An slice backed vector backed by potentially uninitialized memory
149pub type SliceVec<'a, T> = GenericVec<T, &'a mut [MaybeUninit<T>]>;
150
151/// Creates a new uninit array, See [`MaybeUninit::uninit_array`]
152pub fn uninit_array<T, const N: usize>() -> [MaybeUninit<T>; N] {
153    unsafe { MaybeUninit::<[MaybeUninit<T>; N]>::uninit().assume_init() }
154}
155
156/// Create a new generic vector
157///
158/// Because this can create any generic vector, you will likely
159/// need to add some type annotations when you use it,
160///
161/// ```rust
162/// # use cl_generic_vec::{gvec, ArrayVec};
163/// let x: ArrayVec<i32, 2> = gvec![0, 1];
164/// assert_eq!(x, [0, 1]);
165/// ```
166#[macro_export]
167#[cfg(feature = "nightly")]
168macro_rules! gvec {
169    ($expr:expr; $n:expr) => {{
170        let len = $n;
171        let mut vec = $crate::GenericVec::with_capacity(len);
172        vec.grow(len, $expr);
173        vec
174    }};
175    ($($expr:expr),*) => {{
176        let expr = [$($expr),*];
177        let mut vec = $crate::GenericVec::with_capacity(expr.len());
178        unsafe { vec.push_array_unchecked(expr); }
179        vec
180    }};
181}
182
183#[doc(hidden)]
184#[macro_export]
185macro_rules! count {
186    () => { 0 };
187    ($($a:tt $b:tt)*) => { $crate::count!($($a)*) << 1 };
188    ($c:tt $($a:tt $b:tt)*) => { ($crate::count!($($a)*) << 1) | 1 };
189}
190
191/// Create a new generic vector
192///
193/// Because this can create any generic vector, you will likely
194/// need to add some type annotations when you use it,
195///
196/// ```rust
197/// # use cl_generic_vec::{gvec, ArrayVec};
198/// let x: ArrayVec<i32, 4> = gvec![1, 2, 3, 4];
199/// assert_eq!(x, [1, 2, 3, 4]);
200/// ```
201#[macro_export]
202#[cfg(not(feature = "nightly"))]
203macro_rules! gvec {
204    ($expr:expr; $n:expr) => {{
205        let len = $n;
206        let mut vec = $crate::GenericVec::with_capacity(len);
207        vec.grow(len, $expr);
208        vec
209    }};
210    ($($expr:expr),*) => {{
211        let mut vec = $crate::GenericVec::with_capacity($crate::count!($(($expr))*));
212        unsafe {
213            $(vec.push_unchecked($expr);)*
214        }
215        vec
216    }};
217}
218
219/// Save the changes to [`GenericVec::spare_capacity_mut`]
220///
221/// $orig - a mutable reference to a [`GenericVec`]
222/// $spare - the [`SliceVec`] that was obtained from [`$orig.spare_capacity_mut()`]
223///
224/// # Safety
225///
226/// `$spare` should be the [`SliceVec`] returned by `$orig.spare_capacity_mut()`
227#[macro_export]
228macro_rules! save_spare {
229    ($spare:expr, $orig:expr) => {{
230        let spare: $crate::SliceVec<_> = $spare;
231        let spare = $crate::core::mem::ManuallyDrop::new(spare);
232        let len = spare.len();
233        let ptr = spare.as_ptr();
234        let orig: &mut $crate::GenericVec<_, _> = $orig;
235        $crate::validate_spare(ptr, orig);
236        let len = len + orig.len();
237        $orig.set_len_unchecked(len);
238    }};
239}
240
241#[doc(hidden)]
242pub fn validate_spare<T>(spare_ptr: *const T, orig: &[T]) {
243    debug_assert!(
244        unsafe { orig.as_ptr().add(orig.len()) == spare_ptr },
245        "Tried to use `save_spare!` with a `SliceVec` that was not obtained from `GenricVec::spare_capacity_mut`. \
246         This is undefined behavior on release mode!"
247    );
248}
249
250/// A vector type that can be backed up by a variety of different backends
251/// including slices, arrays, and the heap.
252#[repr(C)]
253pub struct GenericVec<T, S: ?Sized + Storage<Item = T>> {
254    len: usize,
255    storage: S,
256}
257
258unsafe fn slice_assume_init_ref<T>(slice: &[MaybeUninit<T>]) -> &[T] {
259    // SAFETY: casting `slice` to a `*const [T]` is safe since the caller guarantees that
260    // `slice` is initialized, and `MaybeUninit` is guaranteed to have the same layout as `T`.
261    // The pointer obtained is valid since it refers to memory owned by `slice` which is a
262    // reference and thus guaranteed to be valid for reads.
263    unsafe { &*(slice as *const [MaybeUninit<T>] as *const [T]) }
264}
265
266unsafe fn slice_assume_init_mut<T>(slice: &mut [MaybeUninit<T>]) -> &mut [T] {
267    // SAFETY: similar to safety notes for `slice_get_ref`, but we have a
268    // mutable reference which is also guaranteed to be valid for writes.
269    unsafe { &mut *(slice as *mut [MaybeUninit<T>] as *mut [T]) }
270}
271
272impl<S: ?Sized + Storage> Deref for SimpleVec<S> {
273    type Target = [S::Item];
274
275    fn deref(&self) -> &Self::Target {
276        let len = self.len;
277        // The first `len` elements are guaranteed to be initialized
278        // as part of the guarantee on `self.set_len_unchecked`
279        unsafe { slice_assume_init_ref(&self.storage.as_ref()[..len]) }
280    }
281}
282
283impl<S: ?Sized + Storage> DerefMut for SimpleVec<S> {
284    fn deref_mut(&mut self) -> &mut Self::Target {
285        let len = self.len;
286        // The first `len` elements are guaranteed to be initialized
287        // as part of the guarantee on `self.set_len_unchecked`
288        unsafe { slice_assume_init_mut(&mut self.storage.as_mut()[..len]) }
289    }
290}
291
292impl<T, S: ?Sized + Storage<Item = T>> Drop for GenericVec<T, S> {
293    fn drop(&mut self) {
294        // The first `len` elements are guaranteed to be initialized
295        // as part of the guarantee on `self.set_len_unchecked`
296        // These elements should be dropped when the `GenericVec` gets dropped/
297        // The storage will clean it's self up on drop
298        unsafe { ptr::drop_in_place(self.as_mut_slice()) }
299    }
300}
301
302impl<S: Storage> SimpleVec<S> {
303    /// Create a new empty `GenericVec` with the given backend
304    ///
305    /// ```rust
306    /// use cl_generic_vec::{ArrayVec, uninit_array};
307    /// let vec = ArrayVec::<i32, 4>::with_storage(uninit_array());
308    /// ```
309    pub fn with_storage(storage: S) -> Self {
310        Self::with_storage_len(storage, 0)
311    }
312
313    fn with_storage_len(storage: S, len: usize) -> Self {
314        Self { len, storage }
315    }
316}
317
318impl<S: raw::StorageWithCapacity> SimpleVec<S> {
319    /// Create a new empty `GenericVec` with the backend with at least the given capacity
320    pub fn with_capacity(capacity: usize) -> Self {
321        Self::with_storage(S::with_capacity(capacity))
322    }
323
324    #[inline]
325    #[allow(non_snake_case)]
326    fn __with_capacity__const_capacity_checked(capacity: usize, old_capacity: Option<usize>) -> Self {
327        Self::with_storage(S::__with_capacity__const_capacity_checked(capacity, old_capacity))
328    }
329}
330
331unsafe fn tm_array<T, U, const N: usize>(array: [T; N]) -> [U; N] {
332    let array = ManuallyDrop::new(array);
333    unsafe { array.as_ptr().cast::<[U; N]>().read() }
334}
335
336impl<T, const N: usize> ArrayVec<T, N> {
337    /// Create a new empty `ArrayVec`
338    pub fn new() -> Self {
339        let uninit = MaybeUninit::<[T; N]>::uninit();
340        let uninit = unsafe { tm_array::<T, MaybeUninit<T>, N>(MaybeUninit::assume_init(uninit)) };
341        Self::with_storage(uninit)
342    }
343
344    /// Create a new full `ArrayVec`
345    pub fn from_array(array: [T; N]) -> Self {
346        // Safety:
347        // The two arrays have exactly the same representation
348        // and the code is taking ownership of the maybeuninit structure,
349        // specifying an initialised count of N, so it's still known to be
350        // initialised.
351        let storage = unsafe { tm_array(array) };
352        Self { len: N, storage }
353    }
354
355    /// Convert this `ArrayVec` into an array
356    ///
357    /// # Panics
358    ///
359    /// Panics if the the collection is not full
360    pub fn into_array(self) -> [T; N] {
361        match self.try_into_array() {
362            Ok(a) => a,
363            _ => panic!("ArrayVec is not full"),
364        }
365    }
366
367    /// Convert this `ArrayVec` into an array
368    ///
369    /// # Errors
370    ///
371    /// errors if the the collection is not full
372    pub fn try_into_array(self) -> Result<[T; N], Self> {
373        if self.is_full() {
374            let this = ManuallyDrop::new(self);
375
376            // Safety: we have just asserted that the full array is initialised
377            // unsafe { MaybeUninit::array_assume_init(self.storage) }
378            Ok(unsafe { this.storage.as_ptr().cast::<[T; N]>().read() })
379        } else {
380            Err(self)
381        }
382    }
383}
384
385#[cfg(feature = "alloc")]
386#[cfg_attr(doc, doc(cfg(feature = "alloc")))]
387impl<T> HeapVec<T> {
388    /// Create a new empty `HeapVec`
389    pub fn new() -> Self {
390        Self {
391            len: 0,
392            storage: Box::<[MaybeUninit<T>]>::default(),
393        }
394    }
395}
396
397#[cfg(any(doc, all(feature = "nightly", feature = "alloc")))]
398#[cfg_attr(doc, doc(cfg(all(feature = "nightly", feature = "alloc"))))]
399impl<T, A: std::alloc::Allocator> HeapVec<T, A> {
400    /// Create a new empty `HeapVec` with the given allocator
401    pub fn with_alloc(alloc: A) -> Self {
402        Self::with_storage(Box::new_uninit_slice_in(0, alloc))
403    }
404}
405
406impl<'a, T> SliceVec<'a, T> {
407    /// Create a new empty `SliceVec`.
408    ///
409    /// # Safety
410    /// The contents of the slice should be completely uninitialised
411    pub unsafe fn new(slice: &'a mut [MaybeUninit<T>]) -> Self {
412        Self::with_storage(slice)
413    }
414
415    /// Create a new full `SliceVec`
416    pub fn full(slice: &'a mut [T]) -> Self {
417        let len = slice.len();
418        let storage = unsafe { &mut *(slice as *mut [T] as *mut [MaybeUninit<T>]) };
419        Self::with_storage_len(storage, len)
420    }
421}
422
423impl<S: Storage> SimpleVec<S> {
424    /// Convert a `GenericVec` into a length-storage pair
425    pub fn into_raw_parts(self) -> (usize, S) {
426        let this = core::mem::ManuallyDrop::new(self);
427        unsafe { (this.len, core::ptr::read(&this.storage)) }
428    }
429
430    /// Create a `GenericVec` from a length-storage pair
431    ///
432    /// # Safety
433    ///
434    /// the length must be less than `raw.capacity()` and
435    /// all elements in the range `0..length`, must be initialized
436    ///
437    /// # Panic
438    ///
439    /// If the given storage cannot hold type `T`, then this method will panic
440    #[cfg(not(feature = "nightly"))]
441    pub unsafe fn from_raw_parts(len: usize, storage: S) -> Self {
442        Self { len, storage }
443    }
444}
445
446#[cfg(feature = "nightly")]
447impl<S: Storage> SimpleVec<S> {
448    /// Create a `GenericVec` from a length-storage pair
449    ///
450    /// Note: this is only const with the `nightly` feature enabled
451    ///
452    /// # Safety
453    ///
454    /// the length must be less than `raw.capacity()` and
455    /// all elements in the range `0..length`, must be initialized
456    ///
457    /// # Panic
458    ///
459    /// If the given storage cannot hold type `T`, then this method will panic
460    pub const unsafe fn from_raw_parts(len: usize, storage: S) -> Self {
461        Self { len, storage }
462    }
463}
464
465impl<S: ?Sized + Storage> SimpleVec<S> {
466    /// Returns the number of elements the vector can hold without reallocating or panicing.
467    pub fn capacity(&self) -> usize {
468        if core::mem::size_of::<S::Item>() == 0 {
469            isize::MAX as usize
470        } else {
471            self.storage.as_ref().len()
472        }
473    }
474
475    /// Returns true if and only if the vector contains no elements.
476    pub fn is_empty(&self) -> bool {
477        self.len() == 0
478    }
479
480    /// Returns true if and only if the vector's length is equal to it's capacity.
481    pub fn is_full(&self) -> bool {
482        self.len() == self.capacity()
483    }
484
485    /// Returns the length of the spare capacity of the `GenericVec`
486    pub fn remaining_capacity(&self) -> usize {
487        self.capacity().wrapping_sub(self.len())
488    }
489
490    /// Set the length of a vector
491    ///
492    /// # Safety
493    ///
494    /// * `new_len` must be less than or equal to `capacity()`.
495    /// * The elements at `old_len..new_len` must be initialized.
496    pub unsafe fn set_len_unchecked(&mut self, len: usize) {
497        self.len = len;
498    }
499
500    /// Set the length of a vector
501    ///
502    /// # Panics
503    /// If the length is set to be larger than the capacity
504    ///
505    /// # Safety
506    ///
507    /// * The elements at `old_len..new_len` must be initialized.
508    pub unsafe fn set_len(&mut self, len: usize) {
509        // Safety
510        //
511        // The storage only contains initialized data, and we check that
512        // the given length is smaller than the capacity
513        unsafe {
514            assert!(
515                len <= self.capacity(),
516                "Tried to set the length to larger than the capacity"
517            );
518            self.set_len_unchecked(len);
519        }
520    }
521
522    /// Extracts a slice containing the entire vector.
523    ///
524    /// Equivalent to &s[..].
525    pub fn as_slice(&self) -> &[S::Item] {
526        self
527    }
528
529    /// Extracts a mutable slice containing the entire vector.
530    ///
531    /// Equivalent to &mut s[..].
532    pub fn as_mut_slice(&mut self) -> &mut [S::Item] {
533        self
534    }
535
536    /// Returns the underlying storage
537    pub fn storage(&self) -> &S {
538        &self.storage
539    }
540
541    /// Returns the underlying storage
542    ///
543    /// # Safety
544    ///
545    /// You must not replace the storage
546    pub unsafe fn storage_mut(&mut self) -> &mut S {
547        &mut self.storage
548    }
549
550    /// Returns the remaining spare capacity of the vector as
551    /// a [`SliceVec<'_, T>`](SliceVec).
552    ///
553    /// Keep in mind that the [`SliceVec<'_, T>`](SliceVec) will drop all elements
554    /// that you push into it when it goes out of scope! If you want
555    /// these modifications to persist then you should use [`save_spare`]
556    /// to persist these writes.
557    ///
558    /// ```
559    /// let mut vec = cl_generic_vec::ArrayVec::<i32, 16>::new();
560    ///
561    /// let mut spare = vec.spare_capacity_mut();
562    /// spare.push(0);
563    /// spare.push(2);
564    /// drop(spare);
565    /// assert_eq!(vec, []);
566    ///
567    /// let mut spare = vec.spare_capacity_mut();
568    /// spare.push(0);
569    /// spare.push(2);
570    /// unsafe { cl_generic_vec::save_spare!(spare, &mut vec) }
571    /// assert_eq!(vec, [0, 2]);
572    /// ```
573    pub fn spare_capacity_mut(&mut self) -> &mut [MaybeUninit<S::Item>] {
574        let len = self.len();
575        &mut self.storage.as_mut()[len..]
576    }
577
578    /// Reserve enough space for at least `additional` elements
579    ///
580    /// # Panics
581    ///
582    /// May panic or abort if it isn't possible to allocate enough space for
583    /// `additional` more elements
584    #[inline]
585    pub fn reserve(&mut self, additional: usize) {
586        #[cold]
587        #[inline(never)]
588        fn allocation_failure(additional: usize) -> ! {
589            panic!("Tried to allocate: {} more space and failed", additional)
590        }
591
592        if self.remaining_capacity() < additional {
593            self.storage.reserve(match self.len().checked_add(additional) {
594                Some(new_capacity) => new_capacity,
595                None => allocation_failure(additional),
596            });
597        }
598    }
599
600    /// Try to reserve enough space for at least `additional` elements
601    ///
602    /// # Errors
603    /// Returns `Err(_)` if it's not possible to reserve enough space
604    #[inline]
605    pub fn try_reserve(&mut self, additional: usize) -> AllocResult {
606        if self.remaining_capacity() < additional {
607            match self.len().checked_add(additional) {
608                Some(new_capacity) => self.storage.try_reserve(new_capacity),
609                None => Err(AllocError),
610            }
611        } else {
612            Ok(())
613        }
614    }
615
616    /// Shortens the vector, keeping the first len elements and dropping the rest.
617    ///
618    /// If len is greater than the vector's current length, this has no effect.
619    ///
620    /// Note that this method has no effect on the allocated capacity of the vector.
621    pub fn truncate(&mut self, len: usize) {
622        if let Some(diff) = self.len().checked_sub(len) {
623            // # Safety
624            //
625            // * the given length is smaller than the current length, so
626            //   all the elements must be initialized
627            // * the elements from `len..self.len()` are valid,
628            //   and should be dropped
629            unsafe {
630                self.set_len_unchecked(len);
631                let ptr = self.as_mut_ptr().add(len);
632                let len = diff;
633                core::ptr::drop_in_place(core::slice::from_raw_parts_mut(ptr, len));
634            }
635        }
636    }
637
638    /// Grows the `GenericVec` in-place by additional elements.
639    ///
640    /// This method requires `T` to implement `Clone`, in order to be able to clone
641    /// the passed value. If you need more flexibility (or want to rely on Default instead of `Clone`),
642    /// use [`GenericVec::grow_with`].
643    ///
644    /// # Panic
645    ///
646    /// May panic or reallocate if the collection is full
647    ///
648    /// # Panic behavor
649    ///
650    /// If `T::clone` panics, then all added items will be dropped. This is different
651    /// from `std`, where on panic, items will stay in the `Vec`. This behavior
652    /// is unstable, and may change in the future.
653    pub fn grow(&mut self, additional: usize, value: S::Item)
654    where
655        S::Item: Clone,
656    {
657        self.reserve(additional);
658        // # Safety
659        //
660        // * we reserved enough space
661        unsafe { extension::Extension::grow(self, additional, value) }
662    }
663
664    /// Grows the `GenericVec` in-place by additional elements.
665    ///
666    /// This method uses a closure to create new values on every push.
667    /// If you'd rather `Clone` a given value, use `GenericVec::resize`.
668    /// If you want to use the `Default` trait to generate values, you
669    /// can pass `Default::default` as the second argument.
670    ///
671    /// # Panic
672    ///
673    /// May panic or reallocate if the collection is full
674    ///
675    /// # Panic behavor
676    ///
677    /// If `F` panics, then all added items will be dropped. This is different
678    /// from `std`, where on panic, items will stay in the `Vec`. This behavior
679    /// is unstable, and may change in the future.
680    pub fn grow_with<F>(&mut self, additional: usize, mut value: F)
681    where
682        F: FnMut() -> S::Item,
683    {
684        // Safety
685        //
686        // * we reserve enough space for `additional` elements
687        // * we use `spare_capacity_mut` to ensure that the items are dropped,
688        //   even on panic
689        // * the `ptr` always stays in bounds
690
691        self.reserve(additional);
692        let spare = self.spare_capacity_mut();
693        let mut writer = unsafe { SliceVec::new(spare) };
694
695        for _ in 0..additional {
696            unsafe {
697                writer.push_unchecked(value());
698            }
699        }
700
701        unsafe {
702            // don't drop the new data!
703            let writer = core::mem::ManuallyDrop::new(writer);
704            let len = writer.len() + self.len();
705            self.set_len_unchecked(len);
706        }
707    }
708
709    /// Resizes the [`GenericVec`] in-place so that `len` is equal to `new_len`.
710    ///
711    /// If `new_len` is greater than `len`, the [`GenericVec`] is extended by the difference,
712    /// with each additional slot filled with value. If `new_len` is less than `len`,
713    /// the [`GenericVec`] is simply truncated.
714    ///
715    /// If you know that `new_len` is larger than `len`, then use [`GenericVec::grow`]
716    ///
717    /// If you know that `new_len` is less than `len`, then use [`GenericVec::truncate`]
718    ///
719    /// This method requires `T` to implement `Clone`, in order to be able to clone
720    /// the passed value. If you need more flexibility (or want to rely on Default
721    /// instead of `Clone`), use [`GenericVec::resize_with`].
722    ///
723    /// # Panic
724    ///
725    /// May panic or reallocate if the collection is full
726    ///
727    /// # Panic behavor
728    ///
729    /// If `F` panics, then all added items will be dropped. This is different
730    /// from `std`, where on panic, items will stay in the `Vec`. This behavior
731    /// is unstable, and may change in the future.
732    pub fn resize(&mut self, new_len: usize, value: S::Item)
733    where
734        S::Item: Clone,
735    {
736        match new_len.checked_sub(self.len()) {
737            Some(0) => (),
738            Some(additional) => self.grow(additional, value),
739            None => self.truncate(new_len),
740        }
741    }
742
743    /// Resizes the [`GenericVec`] in-place so that len is equal to `new_len`.
744    ///
745    /// If `new_len` is greater than `len`, the [`GenericVec`] is extended by the
746    /// difference, with each additional slot filled with the result of calling
747    /// the closure `f`. The return values from `f` will end up in the [`GenericVec`]
748    /// in the order they have been generated.
749    ///
750    /// If `new_len` is less than `len`, the [`GenericVec`] is simply truncated.
751    ///
752    /// If you know that `new_len` is larger than `len`, then use [`GenericVec::grow_with`]
753    ///
754    /// If you know that `new_len` is less than `len`, then use [`GenericVec::truncate`]
755    ///
756    /// This method uses a closure to create new values on every push. If you'd
757    /// rather [`Clone`] a given value, use [`GenericVec::resize`]. If you want to
758    /// use the [`Default`] trait to generate values, you can pass [`Default::default`]
759    /// as the second argument.
760    ///
761    /// # Panic
762    ///
763    /// May panic or reallocate if the collection is full
764    ///
765    /// # Panic behavor
766    ///
767    /// If `F` panics, then all added items will be dropped. This is different
768    /// from `std`, where on panic, items will stay in the `Vec`. This behavior
769    /// is unstable, and may change in the future.
770    pub fn resize_with<F: FnMut() -> S::Item>(&mut self, new_len: usize, value: F) {
771        match new_len.checked_sub(self.len()) {
772            Some(0) => (),
773            Some(additional) => self.grow_with(additional, value),
774            None => self.truncate(new_len),
775        }
776    }
777
778    /// Clears the vector, removing all values.
779    ///
780    /// Note that this method has no effect on the allocated capacity of the vector.
781    pub fn clear(&mut self) {
782        self.truncate(0);
783    }
784
785    /// Appends an element to the back of a collection.
786    ///
787    /// # Panic
788    ///
789    /// May panic or reallocate if the collection is full
790    pub fn push(&mut self, value: S::Item) -> &mut S::Item {
791        if self.len() == self.capacity() {
792            self.reserve(1);
793        }
794
795        // Safety
796        //
797        // * we reserve enough space for 1 more element
798        unsafe { self.push_unchecked(value) }
799    }
800
801    /// Appends the array to the back of a collection.
802    ///
803    /// # Panic
804    ///
805    /// May panic or reallocate if the collection has less than N elements remaining
806    #[cfg(any(doc, feature = "nightly"))]
807    pub fn push_array<const N: usize>(&mut self, value: [S::Item; N]) -> &mut [S::Item; N] {
808        self.reserve(N);
809
810        // Safety
811        //
812        // * we reserve enough space for N more elements
813        unsafe { self.push_array_unchecked(value) }
814    }
815
816    /// Inserts an element at position index within the vector,
817    /// shifting all elements after it to the right.
818    ///
819    /// # Panics
820    ///
821    /// * May panic or reallocate if the collection is full
822    /// * Panics if index > len.
823    pub fn insert(&mut self, index: usize, value: S::Item) -> &mut S::Item {
824        #[cold]
825        #[inline(never)]
826        fn insert_fail(index: usize, len: usize) -> ! {
827            panic!("Tried to insert at {}, but length is {}", index, len);
828        }
829
830        if index > self.len() {
831            insert_fail(index, self.len())
832        }
833
834        if self.is_full() {
835            self.reserve(1);
836        }
837
838        // Safety
839        //
840        // * we reserve enough space for 1 more element
841        // * we verify that index is in bounds
842        unsafe { self.insert_unchecked(index, value) }
843    }
844
845    /// Inserts the array at position index within the vector,
846    /// shifting all elements after it to the right.
847    ///
848    /// # Panics
849    ///
850    /// * May panic or reallocate if the collection has less than N elements remaining
851    /// * Panics if index > len.
852    #[cfg(any(doc, feature = "nightly"))]
853    pub fn insert_array<const N: usize>(&mut self, index: usize, value: [S::Item; N]) -> &mut [S::Item; N] {
854        #[cold]
855        #[inline(never)]
856        fn insert_array_fail(index: usize, size: usize, len: usize) -> ! {
857            panic!(
858                "Tried to insert array of length {} at {}, but length is {}",
859                size, index, len
860            );
861        }
862
863        if index > self.len() {
864            insert_array_fail(index, N, self.len())
865        }
866
867        self.reserve(N);
868
869        // Safety
870        //
871        // * we reserve enough space for N more elements
872        // * we verify that index is in bounds
873        unsafe { self.insert_array_unchecked(index, value) }
874    }
875
876    /// Removes the last element from a vector and returns it
877    ///
878    /// # Panics
879    ///
880    /// Panics if the collection is empty
881    pub fn pop(&mut self) -> S::Item {
882        #[cold]
883        #[inline(never)]
884        fn pop_fail() -> ! {
885            panic!("Tried to pop an element from an empty vector",);
886        }
887
888        if self.is_empty() {
889            pop_fail()
890        }
891
892        // Safety
893        //
894        // * we verify we are not empty
895        unsafe { self.pop_unchecked() }
896    }
897
898    /// Removes the last `N` elements from a vector and returns it
899    ///
900    /// # Panics
901    ///
902    /// Panics if the collection contains less than `N` elements in it
903    #[cfg(any(doc, feature = "nightly"))]
904    pub fn pop_array<const N: usize>(&mut self) -> [S::Item; N] {
905        #[cold]
906        #[inline(never)]
907        fn pop_array_fail(size: usize, len: usize) -> ! {
908            panic!("Tried to pop an array of size {}, a vector of length {}", size, len);
909        }
910
911        if self.len() < N {
912            pop_array_fail(N, self.len())
913        }
914
915        // Safety
916        //
917        // * we verify we have at least N elements
918        unsafe { self.pop_array_unchecked() }
919    }
920
921    /// Removes and returns the element at position index within the vector,
922    /// shifting all elements after it to the left.
923    ///
924    /// # Panics
925    ///
926    /// Panics if `index` is out of bounds.
927    pub fn remove(&mut self, index: usize) -> S::Item {
928        #[cold]
929        #[inline(never)]
930        fn remove_fail(index: usize, len: usize) -> ! {
931            panic!("Tried to remove an element at {}, but length is {}", index, len);
932        }
933
934        if index > self.len() {
935            remove_fail(index, self.len())
936        }
937
938        // Safety
939        //
940        // * we verify that the index is in bounds
941        unsafe { self.remove_unchecked(index) }
942    }
943
944    /// Removes and returns `N` elements at position index within the vector,
945    /// shifting all elements after it to the left.
946    ///
947    /// # Panics
948    ///
949    /// Panics if `index` is out of bounds or if `index + N > len()`
950    #[cfg(any(doc, feature = "nightly"))]
951    pub fn remove_array<const N: usize>(&mut self, index: usize) -> [S::Item; N] {
952        #[cold]
953        #[inline(never)]
954        fn remove_array_fail(index: usize, size: usize, len: usize) -> ! {
955            panic!(
956                "Tried to remove an array length {} at {}, but length is {}",
957                size, index, len
958            );
959        }
960
961        if self.len() < index || self.len().wrapping_sub(index) < N {
962            remove_array_fail(index, N, self.len())
963        }
964
965        // Safety
966        //
967        // * we verify that the index is in bounds
968        // * we verify that there are at least `N` elements
969        //   after the index
970        unsafe { self.remove_array_unchecked(index) }
971    }
972
973    /// Removes an element from the vector and returns it.
974    ///
975    /// The removed element is replaced by the last element of the vector.
976    ///
977    /// This does not preserve ordering, but is O(1).
978    ///
979    /// # Panics
980    ///
981    /// Panics if `index` is out of bounds.
982    pub fn swap_remove(&mut self, index: usize) -> S::Item {
983        #[cold]
984        #[inline(never)]
985        fn swap_remove_fail(index: usize, len: usize) -> ! {
986            panic!("Tried to remove an element at {}, but length is {}", index, len);
987        }
988
989        if index > self.len() {
990            swap_remove_fail(index, self.len())
991        }
992
993        // Safety
994        //
995        // * we verify that the index is in bounds
996        unsafe { self.swap_remove_unchecked(index) }
997    }
998
999    /// Tries to append an element to the back of a collection.
1000    ///
1001    /// # Errors
1002    /// Returns the `Err(value)` if the collection is full
1003    ///
1004    /// Guaranteed to not panic/abort/allocate
1005    pub fn try_push(&mut self, value: S::Item) -> Result<&mut S::Item, S::Item> {
1006        if self.is_full() {
1007            Err(value)
1008        } else {
1009            // Safety
1010            //
1011            // * we reserve enough space for 1 more element
1012            unsafe { Ok(self.push_unchecked(value)) }
1013        }
1014    }
1015
1016    /// Tries to append an array to the back of a collection.
1017    /// Returns the `Err(value)` if the collection doesn't have enough remaining capacity
1018    /// to hold `N` elements.
1019    ///
1020    /// Guaranteed to not panic/abort/allocate
1021    #[cfg(any(doc, feature = "nightly"))]
1022    pub fn try_push_array<const N: usize>(&mut self, value: [S::Item; N]) -> Result<&mut [S::Item; N], [S::Item; N]> {
1023        if self.remaining_capacity() < N {
1024            Err(value)
1025        } else {
1026            // Safety
1027            //
1028            // * we reserve enough space for N more elements
1029            unsafe { Ok(self.push_array_unchecked(value)) }
1030        }
1031    }
1032
1033    /// Inserts an element at position index within the vector,
1034    /// shifting all elements after it to the right.
1035    ///
1036    /// # Errors
1037    /// Returns the `Err(value)` if the collection is full or index is out of bounds
1038    ///
1039    /// Guaranteed to not panic/abort/allocate
1040    pub fn try_insert(&mut self, index: usize, value: S::Item) -> Result<&mut S::Item, S::Item> {
1041        if self.is_full() || index > self.len() {
1042            Err(value)
1043        } else {
1044            // Safety
1045            //
1046            // * we reserve enough space for 1 more element
1047            // * we verify that index is in bounds
1048            unsafe { Ok(self.insert_unchecked(index, value)) }
1049        }
1050    }
1051
1052    /// Inserts an array at position index within the vector,
1053    /// shifting all elements after it to the right.
1054    /// Returns the `Err(value)` if the collection doesn't have enough remaining capacity
1055    /// to hold `N` elements or index is out of bounds
1056    ///
1057    /// Guaranteed to not panic/abort/allocate
1058    #[cfg(any(doc, feature = "nightly"))]
1059    pub fn try_insert_array<const N: usize>(
1060        &mut self,
1061        index: usize,
1062        value: [S::Item; N],
1063    ) -> Result<&mut [S::Item; N], [S::Item; N]> {
1064        if self.capacity().wrapping_sub(self.len()) < N || index > self.len() {
1065            Err(value)
1066        } else {
1067            // Safety
1068            //
1069            // * we reserve enough space for N more elements
1070            // * we verify that index is in bounds
1071            unsafe { Ok(self.insert_array_unchecked(index, value)) }
1072        }
1073    }
1074
1075    /// Removes the last element from a vector and returns it,
1076    /// Returns `None` if the collection is empty
1077    ///
1078    /// Guaranteed to not panic/abort/allocate
1079    pub fn try_pop(&mut self) -> Option<S::Item> {
1080        if self.is_empty() {
1081            None
1082        } else {
1083            // Safety
1084            //
1085            // * we verify we are not empty
1086            unsafe { Some(self.pop_unchecked()) }
1087        }
1088    }
1089
1090    /// Removes the last `N` elements from a vector and returns it,
1091    /// Returns `None` if the collection is has less than N elements
1092    ///
1093    /// Guaranteed to not panic/abort/allocate
1094    #[cfg(any(doc, feature = "nightly"))]
1095    pub fn try_pop_array<const N: usize>(&mut self) -> Option<[S::Item; N]> {
1096        if self.is_empty() {
1097            None
1098        } else {
1099            // Safety
1100            //
1101            // * we verify we have at least N elements
1102            unsafe { Some(self.pop_array_unchecked()) }
1103        }
1104    }
1105
1106    /// Removes and returns the element at position index within the vector,
1107    /// shifting all elements after it to the left.
1108    /// Returns `None` if collection is empty or `index` is out of bounds.
1109    ///
1110    /// Guaranteed to not panic/abort/allocate
1111    pub fn try_remove(&mut self, index: usize) -> Option<S::Item> {
1112        if self.len() < index {
1113            None
1114        } else {
1115            // Safety
1116            //
1117            // * we verify that the index is in bounds
1118            unsafe { Some(self.remove_unchecked(index)) }
1119        }
1120    }
1121
1122    /// Removes and returns the element at position index within the vector,
1123    /// shifting all elements after it to the left.
1124    /// Returns `None` if the collection is has less than N elements
1125    /// or `index` is out of bounds.
1126    ///
1127    /// Guaranteed to not panic/abort/allocate
1128    #[cfg(any(doc, feature = "nightly"))]
1129    pub fn try_remove_array<const N: usize>(&mut self, index: usize) -> Option<[S::Item; N]> {
1130        if self.len() < index || self.len().wrapping_sub(index) < N {
1131            None
1132        } else {
1133            // Safety
1134            //
1135            // * we verify that the index is in bounds
1136            // * we verify that there are at least `N` elements
1137            //   after the index
1138            unsafe { Some(self.remove_array_unchecked(index)) }
1139        }
1140    }
1141
1142    /// Removes an element from the vector and returns it.
1143    /// Returns `None` if collection is empty or `index` is out of bounds.
1144    ///
1145    /// The removed element is replaced by the last element of the vector.
1146    ///
1147    /// This does not preserve ordering, but is O(1).
1148    ///
1149    /// Guaranteed to not panic/abort/allocate
1150    pub fn try_swap_remove(&mut self, index: usize) -> Option<S::Item> {
1151        if index < self.len() {
1152            // Safety
1153            //
1154            // * we verify that the index is in bounds
1155            unsafe { Some(self.swap_remove_unchecked(index)) }
1156        } else {
1157            None
1158        }
1159    }
1160
1161    /// Appends an element to the back of a collection.
1162    ///
1163    /// # Safety
1164    ///
1165    /// the collection must not be full
1166    pub unsafe fn push_unchecked(&mut self, value: S::Item) -> &mut S::Item {
1167        debug_assert_ne!(
1168            self.len(),
1169            self.capacity(),
1170            "Tried to `push_unchecked` past capacity! This is UB in release mode"
1171        );
1172
1173        // Safety
1174        //
1175        // the collection isn't full, so `ptr.add(len)` is valid to write
1176        unsafe {
1177            let len = self.len();
1178            self.set_len_unchecked(len.wrapping_add(1));
1179            let ptr = self.as_mut_ptr().add(len);
1180            ptr.write(value);
1181            &mut *ptr
1182        }
1183    }
1184
1185    /// Appends the array to the back of a collection.
1186    ///
1187    /// # Safety
1188    ///
1189    /// the collection's remaining capacity must be at least N
1190    #[cfg(any(doc, feature = "nightly"))]
1191    pub unsafe fn push_array_unchecked<const N: usize>(&mut self, value: [S::Item; N]) -> &mut [S::Item; N] {
1192        match S::CONST_CAPACITY {
1193            Some(n) if n < N => {
1194                panic!("Tried to push an array larger than the maximum capacity of the vector!")
1195            }
1196            _ => (),
1197        }
1198
1199        // Safety
1200        //
1201        // the collection has at least N remaining elements of capacity left,
1202        // so `ptr.add(len)` is valid to write `N` elements
1203        unsafe {
1204            let len = self.len();
1205            self.set_len_unchecked(len.wrapping_add(N));
1206            let ptr = self.as_mut_ptr();
1207            let out = ptr.add(len) as *mut [S::Item; N];
1208            out.write(value);
1209            &mut *out
1210        }
1211    }
1212
1213    /// Inserts an element at position index within the vector,
1214    /// shifting all elements after it to the right.
1215    ///
1216    /// # Safety
1217    ///
1218    /// * the collection is must not be full
1219    /// * the index must be in bounds
1220    pub unsafe fn insert_unchecked(&mut self, index: usize, value: S::Item) -> &mut S::Item {
1221        unsafe {
1222            debug_assert_ne!(
1223                self.len(),
1224                self.capacity(),
1225                "Tried to `insert_unchecked` past capacity! This is UB in release mode"
1226            );
1227
1228            // Safety
1229            //
1230            // * the index is in bounds
1231            // * the collection is't full so `ptr.add(len)` is valid to write 1 element
1232            let len = self.len();
1233            self.set_len_unchecked(len.wrapping_add(1));
1234            let ptr = self.as_mut().as_mut_ptr().add(index);
1235            ptr.add(1).copy_from(ptr, len.wrapping_sub(index));
1236            ptr.write(value);
1237            &mut *ptr
1238        }
1239    }
1240
1241    /// Inserts an array at position index within the vector,
1242    /// shifting all elements after it to the right.
1243    ///
1244    /// # Safety
1245    ///
1246    /// * the collection's remaining capacity must be at least N
1247    /// * hte index must be in bounds
1248    #[cfg(any(doc, feature = "nightly"))]
1249    pub unsafe fn insert_array_unchecked<const N: usize>(
1250        &mut self,
1251        index: usize,
1252        value: [S::Item; N],
1253    ) -> &mut [S::Item; N] {
1254        match S::CONST_CAPACITY {
1255            Some(n) if n < N => {
1256                panic!("Tried to push an array larger than the maximum capacity of the vector!")
1257            }
1258            _ => (),
1259        }
1260
1261        // Safety
1262        //
1263        // * the index is in bounds
1264        // * the collection has at least N remaining elements of capacity left,
1265        //   so `ptr.add(len)` is valid to write `N` elements
1266        unsafe {
1267            let len = self.len();
1268            self.set_len_unchecked(len.wrapping_add(N));
1269            let ptr = self.as_mut_ptr();
1270            let dist = len.wrapping_sub(index);
1271
1272            let out = ptr.add(index);
1273            out.add(N).copy_from(out, dist);
1274            let out = out as *mut [S::Item; N];
1275            out.write(value);
1276            &mut *out
1277        }
1278    }
1279
1280    /// Removes the last element from a vector and returns it
1281    ///
1282    /// # Safety
1283    ///
1284    /// the collection must not be empty
1285    pub unsafe fn pop_unchecked(&mut self) -> S::Item {
1286        let len = self.len();
1287        debug_assert_ne!(
1288            len, 0,
1289            "Tried to `pop_unchecked` an empty array vec! This is UB in release mode"
1290        );
1291
1292        // Safety
1293        //
1294        // * the collection isn't empty, so `ptr.add(len - 1)` is valid to read
1295        unsafe {
1296            let len = len.wrapping_sub(1);
1297            self.set_len_unchecked(len);
1298            self.as_mut_ptr().add(len).read()
1299        }
1300    }
1301
1302    /// Removes the last `N` elements from a vector and returns it
1303    ///
1304    /// # Safety
1305    ///
1306    /// The collection must contain at least `N` elements in it
1307    #[cfg(any(doc, feature = "nightly"))]
1308    pub unsafe fn pop_array_unchecked<const N: usize>(&mut self) -> [S::Item; N] {
1309        match S::CONST_CAPACITY {
1310            Some(n) if n < N => panic!("Tried to remove {} elements from a {} capacity vector!", N, n),
1311            _ => (),
1312        }
1313
1314        let len = self.len();
1315        debug_assert!(
1316            len > N,
1317            "Tried to remove {} elements from a {} length vector! This is UB in release mode",
1318            N,
1319            len,
1320        );
1321        // Safety
1322        //
1323        // * the collection has at least `N` elements, so `ptr.add(len - N)` is valid to read `N` elements
1324        unsafe {
1325            let len = len.wrapping_sub(N);
1326            self.set_len_unchecked(len);
1327            self.as_mut_ptr().add(len).cast::<[S::Item; N]>().read()
1328        }
1329    }
1330
1331    /// Removes and returns the element at position index within the vector,
1332    /// shifting all elements after it to the left.
1333    ///
1334    /// # Safety
1335    ///
1336    /// the collection must not be empty, and
1337    /// index must be in bounds
1338    pub unsafe fn remove_unchecked(&mut self, index: usize) -> S::Item {
1339        let len = self.len();
1340
1341        debug_assert!(
1342            index <= len,
1343            "Tried to remove an element at index {} from a {} length vector! This is UB in release mode",
1344            index,
1345            len,
1346        );
1347
1348        // Safety
1349        //
1350        // * the index is in bounds
1351        // * the collection isn't empty, so `ptr.add(len - index - 1)` is valid to read
1352        unsafe {
1353            self.set_len_unchecked(len.wrapping_sub(1));
1354            let ptr = self.as_mut().as_mut_ptr().add(index);
1355            let value = ptr.read();
1356            ptr.copy_from(ptr.add(1), len.wrapping_sub(index).wrapping_sub(1));
1357            value
1358        }
1359    }
1360
1361    /// Removes and returns the element at position index within the vector,
1362    /// shifting all elements after it to the left.
1363    ///
1364    /// # Safety
1365    ///
1366    /// the collection must contain at least N elements, and
1367    /// index must be in bounds
1368    #[cfg(any(doc, feature = "nightly"))]
1369    pub unsafe fn remove_array_unchecked<const N: usize>(&mut self, index: usize) -> [S::Item; N] {
1370        match S::CONST_CAPACITY {
1371            Some(n) if n < N => panic!("Tried to remove {} elements from a {} capacity vector!", N, n),
1372            _ => (),
1373        }
1374
1375        let len = self.len();
1376        debug_assert!(
1377            index <= len,
1378            "Tried to remove elements at index {} from a {} length vector! This is UB in release mode",
1379            index,
1380            len,
1381        );
1382        debug_assert!(
1383            len.wrapping_sub(index) > N,
1384            "Tried to remove {} elements from a {} length vector! This is UB in release mode",
1385            N,
1386            len,
1387        );
1388
1389        // Safety
1390        //
1391        // * the index is in bounds
1392        // * the collection isn't empty, so `ptr.add(len - index - N)` is valid to read `N` elements
1393        unsafe {
1394            self.set_len_unchecked(len.wrapping_sub(N));
1395            let ptr = self.as_mut_ptr().add(index);
1396            let value = ptr.cast::<[S::Item; N]>().read();
1397            if N != 0 {
1398                ptr.copy_from(ptr.add(N), len.wrapping_sub(index).wrapping_sub(N));
1399            }
1400            value
1401        }
1402    }
1403
1404    /// Removes an element from the vector and returns it.
1405    ///
1406    /// The removed element is replaced by the last element of the vector.
1407    ///
1408    /// This does not preserve ordering, but is O(1).
1409    ///
1410    /// # Safety
1411    ///
1412    /// the `index` must be in bounds
1413    pub unsafe fn swap_remove_unchecked(&mut self, index: usize) -> S::Item {
1414        // Safety
1415        //
1416        // * the index is in bounds
1417        // * the collection isn't empty
1418        unsafe {
1419            let len = self.len();
1420            self.set_len_unchecked(len.wrapping_sub(1));
1421            let ptr = self.as_mut().as_mut_ptr();
1422            let at = ptr.add(index);
1423            let end = ptr.add(len.wrapping_sub(1));
1424            let value = at.read();
1425            at.copy_from(end, 1);
1426            value
1427        }
1428    }
1429
1430    /// Splits the collection into two at the given index.
1431    ///
1432    /// Returns a newly allocated vector containing the elements in the range `[at, len)`.
1433    /// After the call, the original vector will be left containing the elements `[0, at)`
1434    /// with its previous capacity unchanged.
1435    ///
1436    /// ```rust
1437    /// # use cl_generic_vec::{gvec, SliceVec, uninit_array};
1438    /// # let mut vec_buf = uninit_array::<_, 3>();
1439    /// # let mut vec2_buf = uninit_array::<_, 5>();
1440    /// # let mut vec: SliceVec<_> = unsafe { SliceVec::new(&mut vec_buf) }; vec.extend([1, 2, 3].iter().copied());
1441    /// # let mut vec2: SliceVec<_> = unsafe { SliceVec::new(&mut vec2_buf) }; vec2.extend([4, 5, 6].iter().copied());
1442    /// assert_eq!(vec, [1, 2, 3]);
1443    /// assert_eq!(vec2, [4, 5, 6]);
1444    /// vec.split_off_into(1, &mut vec2);
1445    /// assert_eq!(vec, [1]);
1446    /// assert_eq!(vec2, [4, 5, 6, 2, 3]);
1447    /// ```
1448    ///
1449    /// # Panics
1450    /// If the index is out of bounds
1451    pub fn split_off<B>(&mut self, index: usize) -> GenericVec<S::Item, B>
1452    where
1453        B: raw::StorageWithCapacity<Item = S::Item>,
1454    {
1455        assert!(
1456            index <= self.len(),
1457            "Tried to split at index {}, but length is {}",
1458            index,
1459            self.len()
1460        );
1461
1462        let mut vec = GenericVec::<S::Item, B>::__with_capacity__const_capacity_checked(
1463            self.len().wrapping_sub(index),
1464            S::CONST_CAPACITY,
1465        );
1466
1467        self.split_off_into(index, &mut vec);
1468
1469        vec
1470    }
1471
1472    /// Splits the collection into two at the given index.
1473    ///
1474    /// Appends the elements from the range `[at, len)` to `other`.
1475    /// After the call, the original vector will be left containing the elements `[0, at)`
1476    /// with its previous capacity unchanged.
1477    ///
1478    /// ```rust
1479    /// # use cl_generic_vec::{gvec, SliceVec, uninit_array};
1480    /// # let mut vec_buf = uninit_array::<_, 3>();
1481    /// # let mut vec2_buf = uninit_array::<_, 5>();
1482    /// # let mut vec: SliceVec<_> = unsafe { SliceVec::new(&mut vec_buf) }; vec.extend([1, 2, 3].iter().copied());
1483    /// # let mut vec2: SliceVec<_> = unsafe { SliceVec::new(&mut vec2_buf) }; vec2.extend([4, 5, 6].iter().copied());
1484    /// assert_eq!(vec, [1, 2, 3]);
1485    /// assert_eq!(vec2, [4, 5, 6]);
1486    /// vec.split_off_into(1, &mut vec2);
1487    /// assert_eq!(vec, [1]);
1488    /// assert_eq!(vec2, [4, 5, 6, 2, 3]);
1489    /// ```
1490    ///
1491    /// # Panics
1492    /// If the index is out of bounds
1493    pub fn split_off_into<B>(&mut self, index: usize, other: &mut GenericVec<S::Item, B>)
1494    where
1495        B: raw::Storage<Item = S::Item> + ?Sized,
1496    {
1497        assert!(
1498            index <= self.len(),
1499            "Tried to split at index {}, but length is {}",
1500            index,
1501            self.len()
1502        );
1503
1504        unsafe {
1505            // Safety
1506            //
1507            // * the index is in bounds
1508            // * other has reserved enough space
1509            // * we ignore all elements after index
1510            let slice = self.get_unchecked(index..);
1511            other.reserve(slice.len());
1512            other.extend_from_slice_unchecked(slice);
1513            self.set_len_unchecked(index);
1514        }
1515    }
1516
1517    /// Moves all the elements of `other` into `Self`, leaving `other` empty.
1518    ///
1519    /// Does not change the capacity of either collection.
1520    ///
1521    /// ```rust
1522    /// # use cl_generic_vec::{gvec, SliceVec, uninit_array};
1523    /// # let mut vec_buf = uninit_array::<_, 6>();
1524    /// # let mut vec2_buf = uninit_array::<_, 3>();
1525    /// # let mut vec: SliceVec<_> = unsafe { SliceVec::new(&mut vec_buf) }; vec.extend([1, 2, 3].iter().copied());
1526    /// # let mut vec2: SliceVec<_> = unsafe { SliceVec::new(&mut vec2_buf) }; vec2.extend([4, 5, 6].iter().copied());
1527    /// assert_eq!(vec, [1, 2, 3]);
1528    /// assert_eq!(vec2, [4, 5, 6]);
1529    /// vec.append(&mut vec2);
1530    /// assert_eq!(vec, [1, 2, 3, 4, 5, 6]);
1531    /// assert_eq!(vec2, []);
1532    /// ```
1533    ///
1534    /// # Panic
1535    ///
1536    /// May panic or reallocate if the collection is full
1537    pub fn append<B: Storage<Item = S::Item> + ?Sized>(&mut self, other: &mut GenericVec<S::Item, B>) {
1538        other.split_off_into(0, self);
1539    }
1540
1541    /// Convert the backing storage type, and moves all the elements in `self` to the new vector
1542    pub fn convert<B: raw::StorageWithCapacity<Item = S::Item>>(mut self) -> GenericVec<S::Item, B>
1543    where
1544        S: Sized,
1545    {
1546        self.split_off(0)
1547    }
1548
1549    /// Creates a raw cursor that can be used to remove elements in the specified range.
1550    /// Usage of [`RawCursor`](iter::RawCursor) is `unsafe` because it doesn't do any checks.
1551    /// [`RawCursor`](iter::RawCursor) is meant to be a low level tool to implement fancier
1552    /// iterators, like [`GenericVec::drain`], [`GenericVec::drain_filter`],
1553    /// or [`GenericVec::splice`].
1554    ///
1555    /// # Panic
1556    ///
1557    /// Panics if the starting point is greater than the end point or if the end point
1558    /// is greater than the length of the vector.
1559    #[inline]
1560    pub fn raw_cursor<R>(&mut self, range: R) -> iter::RawCursor<'_, S>
1561    where
1562        R: RangeBounds<usize>,
1563    {
1564        let range = slice::check_range(self.len(), range);
1565        iter::RawCursor::new(self, range)
1566    }
1567
1568    /// Creates a cursor that can be used to remove elements in the specified range.
1569    ///
1570    /// # Panic
1571    ///
1572    /// Panics if the starting point is greater than the end point or if the end point
1573    /// is greater than the length of the vector.
1574    #[inline]
1575    pub fn cursor<R>(&mut self, range: R) -> iter::Cursor<'_, S>
1576    where
1577        R: RangeBounds<usize>,
1578    {
1579        iter::Cursor::new(self.raw_cursor(range))
1580    }
1581
1582    /// Creates a draining iterator that removes the specified range in the
1583    /// vector and yields the removed items.
1584    ///
1585    /// When the iterator is dropped, all elements in the range are removed from
1586    /// the vector, even if the iterator was not fully consumed. If the iterator
1587    /// is not dropped (with `mem::forget` for example), it is unspecified how many
1588    /// elements are removed.
1589    ///
1590    /// # Panic
1591    ///
1592    /// Panics if the starting point is greater than the end point or if the end point
1593    /// is greater than the length of the vector.
1594    #[inline]
1595    pub fn drain<R>(&mut self, range: R) -> iter::Drain<'_, S>
1596    where
1597        R: RangeBounds<usize>,
1598    {
1599        iter::Drain::new(self.raw_cursor(range))
1600    }
1601
1602    /// Creates an iterator which uses a closure to determine if an element should be removed.
1603    ///
1604    /// If the closure returns true, then the element is removed and yielded.
1605    /// If the closure returns false, the element will remain in the vector
1606    /// and will not be yielded by the iterator.
1607    ///
1608    /// # Panic
1609    ///
1610    /// Panics if the starting point is greater than the end point or if the end point
1611    /// is greater than the length of the vector.
1612    #[inline]
1613    pub fn drain_filter<R, F>(&mut self, range: R, f: F) -> iter::DrainFilter<'_, S, F>
1614    where
1615        R: RangeBounds<usize>,
1616        F: FnMut(&mut S::Item) -> bool,
1617    {
1618        iter::DrainFilter::new(self.raw_cursor(range), f)
1619    }
1620
1621    /// Creates a splicing iterator that replaces the specified range in the vector with
1622    /// the given `replace_with` iterator and yields the removed items. `replace_with` does
1623    /// not need to be the same length as range.
1624    ///
1625    /// range is removed even if the iterator is not consumed until the end.
1626    ///
1627    /// It is unspecified how many elements are removed from the vector if the
1628    /// [`Splice`](iter::Splice) value is leaked.
1629    ///
1630    /// The input iterator `replace_with` is only consumed when the [`Splice`](iter::Splice)
1631    /// value is dropped
1632    ///
1633    /// # Panic
1634    ///
1635    /// Panics if the starting point is greater than the end point or if the end point
1636    /// is greater than the length of the vector.
1637    #[inline]
1638    pub fn splice<R, I>(&mut self, range: R, replace_with: I) -> iter::Splice<'_, S, I::IntoIter>
1639    where
1640        R: RangeBounds<usize>,
1641        I: IntoIterator<Item = S::Item>,
1642    {
1643        iter::Splice::new(self.raw_cursor(range), replace_with.into_iter())
1644    }
1645
1646    /// Retains only the elements specified by the predicate.
1647    ///
1648    /// In other words, remove all elements `e` such that `f(e)` returns false.
1649    /// This method operates in place, visiting each element exactly once in
1650    /// the original order, and preserves the order of the retained elements.
1651    #[inline]
1652    pub fn retain<F>(&mut self, f: F)
1653    where
1654        F: FnMut(&mut S::Item) -> bool,
1655    {
1656        fn not<F: FnMut(&mut T) -> bool, T>(mut f: F) -> impl FnMut(&mut T) -> bool {
1657            move |value| !f(value)
1658        }
1659        self.drain_filter(.., not(f));
1660    }
1661
1662    /// Shallow copies and appends all elements in a slice to the `GenericVec`.
1663    ///
1664    /// # Safety
1665    ///
1666    /// * You must not drop any of the elements in `slice`
1667    /// * There must be at least `slice.len()` remaining capacity in the vector
1668    pub unsafe fn extend_from_slice_unchecked(&mut self, slice: &[S::Item]) {
1669        debug_assert!(
1670            self.remaining_capacity() >= slice.len(),
1671            "Not enough capacity to hold the slice"
1672        );
1673
1674        unsafe {
1675            let len = self.len();
1676            self.as_mut_ptr()
1677                .add(len)
1678                .copy_from_nonoverlapping(slice.as_ptr(), slice.len());
1679            self.set_len_unchecked(len.wrapping_add(slice.len()));
1680        }
1681    }
1682
1683    /// Clones and appends all elements in a slice to the `GenericVec`.
1684    ///
1685    /// Iterates over the slice other, clones each element, and then appends
1686    /// it to this `GenericVec`. The other vector is traversed in-order.
1687    ///
1688    /// Note that this function is same as extend except that it is specialized
1689    /// to work with slices instead. If and when Rust gets specialization this
1690    /// function will likely be deprecated (but still available).
1691    ///
1692    /// # Panic behavor
1693    ///
1694    /// If `T::clone` panics, then all newly added items will be dropped. This is different
1695    /// from `std`, where on panic, newly added items will stay in the `Vec`. This behavior
1696    /// is unstable, and may change in the future.
1697    pub fn extend_from_slice(&mut self, slice: &[S::Item])
1698    where
1699        S::Item: Clone,
1700    {
1701        self.reserve(slice.len());
1702
1703        // Safety
1704        //
1705        // We reserved enough space
1706        unsafe { extension::Extension::extend_from_slice(self, slice) }
1707    }
1708
1709    /// Replaces all of the current elements with the ones in the slice
1710    ///
1711    /// equivalent to the following
1712    ///
1713    /// ```rust
1714    /// # let slice = [];
1715    /// # let mut buffer = cl_generic_vec::uninit_array::<_, 0>();
1716    /// # let mut vec = unsafe { cl_generic_vec::SliceVec::<()>::new(&mut buffer) };
1717    /// vec.clear();
1718    /// vec.extend_from_slice(&slice);
1719    /// ```
1720    ///
1721    /// # Panic
1722    ///
1723    /// May try to panic/reallocate if there is not enough capacity for the slice
1724    pub fn clone_from(&mut self, source: &[S::Item])
1725    where
1726        S::Item: Clone,
1727    {
1728        // If the `self` is longer than `source`, remove excess
1729        self.truncate(source.len());
1730
1731        // `self` is now at most the same length as `source`
1732        //
1733        // * `init.len() == self.len()`
1734        // * tail is the rest of the `source`, in the case
1735        //     that `self` is smaller than `source`
1736        let (init, tail) = source.split_at(self.len());
1737
1738        // Clone in the beginning, using `slice::clone_from_slice`
1739        self.clone_from_slice(init);
1740
1741        // Append the remaining elements
1742        self.extend_from_slice(tail);
1743    }
1744
1745    /// Removes all but the first of consecutive elements in the vector satisfying
1746    /// a given equality relation.
1747    ///
1748    /// The `same_bucket` function is passed references to two elements from the
1749    /// vector and must determine if the elements compare equal. The elements
1750    /// are passed in opposite order from their order in the slice, so if
1751    /// `same_bucket(a, b)` returns true, a is removed.
1752    ///
1753    /// If the vector is sorted, this removes all duplicates.
1754    pub fn dedup_by<F>(&mut self, same_bucket: F)
1755    where
1756        F: FnMut(&mut S::Item, &mut S::Item) -> bool,
1757    {
1758        let (a, _) = slice::partition_dedup_by(self.as_mut_slice(), same_bucket);
1759        let new_len = a.len();
1760        self.truncate(new_len);
1761    }
1762
1763    /// Removes all but the first of consecutive elements in the vector that resolve to the same key.
1764    ///
1765    /// If the vector is sorted, this removes all duplicates.
1766    pub fn dedup_by_key<F, K>(&mut self, key: F)
1767    where
1768        F: FnMut(&mut S::Item) -> K,
1769        K: PartialEq,
1770    {
1771        #[inline]
1772        fn key_to_same_bucket<T, F, K>(mut f: F) -> impl FnMut(&mut T, &mut T) -> bool
1773        where
1774            F: FnMut(&mut T) -> K,
1775            K: PartialEq,
1776        {
1777            #[inline]
1778            move |a, b| {
1779                let a = f(a);
1780                let b = f(b);
1781                a == b
1782            }
1783        }
1784
1785        self.dedup_by(key_to_same_bucket(key));
1786    }
1787
1788    /// Removes all but the first of consecutive elements in the vector that resolve to the same key.
1789    ///
1790    /// If the vector is sorted, this removes all duplicates.
1791    pub fn dedup<F, K>(&mut self)
1792    where
1793        S::Item: PartialEq,
1794    {
1795        #[inline]
1796        fn eq_to_same_buckets<T, F>(mut f: F) -> impl FnMut(&mut T, &mut T) -> bool
1797        where
1798            F: FnMut(&T, &T) -> bool,
1799        {
1800            #[inline]
1801            move |a, b| f(a, b)
1802        }
1803
1804        self.dedup_by(eq_to_same_buckets(PartialEq::eq));
1805    }
1806}