offset_vec/
lib.rs

1#![doc = include_str!("../README.md")]
2#![no_std]
3#![cfg_attr(docsrs, feature(doc_cfg))]
4
5extern crate alloc;
6
7#[cfg(doc)]
8use alloc::{vec::Vec, string::String};
9
10use core::{
11    iter::once,
12    ops::{Bound, Deref, DerefMut, Index, IndexMut, Range, RangeBounds},
13    slice::SliceIndex,
14};
15
16mod util;
17mod slice;
18mod offset;
19mod vec_like;
20
21pub use slice::*;
22pub use offset::*;
23pub use vec_like::*;
24
25mod externs {
26    mod core_impls;
27}
28
29/// Packer for [`Vec`] and [`String`] etc
30///
31/// For all methods index add a `offset`
32///
33/// Create from [`Offset::offset`] or [`create`]
34///
35/// # Examples
36///
37/// ```
38/// use offset_vec::Offset;
39///
40/// let mut vec = vec![0, 1, 2, 3, 4];
41/// let mut vec1 = vec.offset_mut(2);
42///
43/// assert_eq!(vec1, [2, 3, 4]);
44/// assert_eq!(vec1[1], 3);
45///
46/// vec1[1] += 2;
47/// assert_eq!(vec, [0, 1, 2, 5, 4]);
48/// ```
49#[derive(Debug, Clone, Default)]
50pub struct OffsetVec<V: VecLike> {
51    vec: V,
52    offset: usize,
53}
54
55impl<V: VecLike> Deref for OffsetVec<V> {
56    type Target = V::Slice;
57
58    #[inline]
59    fn deref(&self) -> &Self::Target {
60        let offset = self.offset;
61        let slice = self.vec.as_slice();
62        &slice[offset..]
63    }
64}
65
66impl<V: VecLike> DerefMut for OffsetVec<V> {
67    #[inline]
68    fn deref_mut(&mut self) -> &mut Self::Target {
69        let offset = self.offset;
70        let slice_mut = self.vec.as_mut_slice();
71        &mut slice_mut[offset..]
72    }
73}
74
75impl<V, I> Index<I> for OffsetVec<V>
76where V: VecLike,
77      I: SliceIndex<V::Slice>,
78      V::Slice: Index<I>,
79{
80    type Output = <V::Slice as Index<I>>::Output;
81
82    #[track_caller]
83    fn index(&self, index: I) -> &Self::Output {
84        let slice = &**self;
85        &slice[index]
86    }
87}
88
89impl<V, I> IndexMut<I> for OffsetVec<V>
90where V: VecLike,
91      I: SliceIndex<V::Slice>,
92      V::Slice: IndexMut<I>,
93{
94    #[track_caller]
95    fn index_mut(&mut self, index: I) -> &mut Self::Output {
96        let slice = &mut **self;
97        &mut slice[index]
98    }
99}
100
101impl<V: VecLike> OffsetVec<V> {
102    /// Get original vector
103    ///
104    /// # Examples
105    ///
106    /// ```
107    /// use offset_vec::Offset;
108    ///
109    /// let mut vec = vec![0, 1, 2, 3, 4];
110    /// let mut vec1 = vec.offset_mut(2);
111    ///
112    /// assert_eq!(vec1, [2, 3, 4]);
113    /// assert_eq!(vec1.origin_vec(), &&mut vec![0, 1, 2, 3, 4]);
114    /// ```
115    #[inline]
116    pub fn origin_vec(&self) -> &V {
117        &self.vec
118    }
119
120    /// Get mutable original vector
121    ///
122    /// # Examples
123    ///
124    /// ```
125    /// use offset_vec::Offset;
126    ///
127    /// let mut vec = vec![0, 1, 2, 3, 4];
128    /// let mut vec1 = vec.offset_mut(2);
129    ///
130    /// assert_eq!(vec1, [2, 3, 4]);
131    /// assert_eq!(vec1.origin_vec_mut(), &mut &mut vec![0, 1, 2, 3, 4]);
132    ///
133    /// vec1.origin_vec_mut()[3] += 2;
134    /// assert_eq!(vec1, [2, 5, 4]);
135    /// ```
136    #[inline]
137    pub fn origin_vec_mut(&mut self) -> &mut V {
138        &mut self.vec
139    }
140
141    /// Consume [`OffsetVec`] into packed original vector
142    ///
143    /// # Examples
144    ///
145    /// ```
146    /// use offset_vec::Offset;
147    ///
148    /// let vec = vec![0, 1, 2, 3, 4];
149    /// let mut vec1 = vec.offset(2);
150    ///
151    /// assert_eq!(vec1, [2, 3, 4]);
152    /// assert_eq!(vec1.into_origin_vec(), vec![0, 1, 2, 3, 4]);
153    /// ```
154    #[inline]
155    pub fn into_origin_vec(self) -> V {
156        self.vec
157    }
158
159    /// Extracts a slice containing the offset vector.
160    ///
161    /// Equivalent to &s[..].
162    ///
163    /// # Examples
164    ///
165    /// ```
166    /// use offset_vec::Offset;
167    ///
168    /// let vec = vec![0, 1, 2, 3, 4];
169    /// let mut vec1 = vec.offset(2);
170    ///
171    /// assert_eq!(vec1.as_slice(), &[2, 3, 4]);
172    /// assert_eq!(&vec1[..], &[2, 3, 4]);
173    /// ```
174    #[inline]
175    pub fn as_slice(&self) -> &V::Slice {
176        self
177    }
178
179    /// Extracts a mutable slice containing the offset vector.
180    ///
181    /// Equivalent to &mut s[..].
182    ///
183    /// # Examples
184    ///
185    /// ```
186    /// use offset_vec::Offset;
187    ///
188    /// let vec = vec![0, 1, 2, 3, 4];
189    /// let mut vec1 = vec.offset(2);
190    ///
191    /// assert_eq!(vec1.as_mut_slice(), &mut [2, 3, 4]);
192    /// assert_eq!(&mut vec1[..], &mut [2, 3, 4]);
193    /// ```
194    #[inline]
195    pub fn as_mut_slice(&mut self) -> &mut V::Slice {
196        self
197    }
198
199    pub fn iter<'a>(&'a self) -> <&'a V::Slice as IntoIterator>::IntoIter
200    where &'a V::Slice: IntoIterator
201    {
202        self.as_slice().into_iter()
203    }
204
205    pub fn iter_mut<'a>(&'a mut self) -> <&'a mut V::Slice as IntoIterator>::IntoIter
206    where &'a mut V::Slice: IntoIterator
207    {
208        self.as_mut_slice().into_iter()
209    }
210
211    /// `self.len() == 0`
212    #[inline]
213    pub fn is_empty(&self) -> bool {
214        self.len() == 0
215    }
216
217    /// Get offset vector length
218    ///
219    /// # Examples
220    ///
221    /// ```
222    /// use offset_vec::Offset;
223    ///
224    /// let vec = vec![0, 1, 2, 3, 4];
225    /// let mut vec1 = vec.offset(2);
226    ///
227    /// assert_eq!(vec1.len(), 3);
228    /// assert_eq!(vec1.origin_vec().len(), 5);
229    /// ```
230    #[inline]
231    pub fn len(&self) -> usize {
232        self.vec.len() - self.offset
233    }
234
235    /// Get offset vector capacity
236    ///
237    /// # Examples
238    ///
239    /// ```
240    /// use offset_vec::Offset;
241    ///
242    /// let mut vec = Vec::with_capacity(5);
243    /// vec.extend([0, 1, 2, 3, 4]);
244    /// let mut vec1 = vec.offset(2);
245    ///
246    /// assert_eq!(3, vec1.capacity());
247    /// assert_eq!(5, vec1.origin_vec().capacity());
248    /// ```
249    #[inline]
250    pub fn capacity(&self) -> usize {
251        self.vec.capacity() - self.offset
252    }
253
254    pub fn reserve(&mut self, additional: usize) {
255        self.vec.reserve(additional);
256    }
257
258    pub fn reserve_exact(&mut self, additional: usize) {
259        self.vec.reserve_exact(additional);
260    }
261
262    pub fn shrink_to_fit(&mut self) {
263        self.vec.shrink_to_fit();
264    }
265
266    pub fn shrink_to(&mut self, min_capacity: usize) {
267        self.vec.shrink_to(min_capacity);
268    }
269
270    /// Get offset
271    ///
272    /// # Examples
273    ///
274    /// ```
275    /// use offset_vec::Offset;
276    ///
277    /// let vec = vec![0, 1, 2, 3, 4];
278    /// let vec1 = vec.offset(2);
279    ///
280    /// assert_eq!(vec1.origin_offset(), 2);
281    ///
282    /// let vec2 = vec1.offset(1);
283    /// assert_eq!(vec2.origin_offset(), 3);
284    /// ```
285    pub fn origin_offset(&self) -> usize {
286        self.offset
287    }
288
289    /// Push a value
290    ///
291    /// # Examples
292    ///
293    /// ```
294    /// use offset_vec::Offset;
295    ///
296    /// let mut vec = vec![0, 1, 2, 3, 4];
297    /// let mut vec1 = vec.offset_mut(2);
298    ///
299    /// assert_eq!(vec1, [2, 3, 4]);
300    /// vec1.push(5);
301    /// assert_eq!(vec1, [2, 3, 4, 5]);
302    /// assert_eq!(vec, [0, 1, 2, 3, 4, 5]);
303    /// ```
304    pub fn push(&mut self, value: V::Elem) {
305        self.vec.push(value);
306    }
307
308    /// Pop a value
309    ///
310    /// # Examples
311    ///
312    /// ```
313    /// use offset_vec::Offset;
314    ///
315    /// let mut vec = vec![0, 1, 2, 3];
316    /// let mut vec1 = vec.offset_mut(2);
317    ///
318    /// assert_eq!(vec1, [2, 3]);
319    /// assert_eq!(vec1.pop(), Some(3));
320    /// assert_eq!(vec1, [2]);
321    /// assert_eq!(vec1.pop(), Some(2));
322    /// assert_eq!(vec1, []);
323    /// assert_eq!(vec1.pop(), None);
324    /// assert_eq!(vec1, []);
325    ///
326    /// assert_eq!(vec1.origin_vec(), &&mut [0, 1]);
327    /// assert_eq!(vec, [0, 1]);
328    /// ```
329    pub fn pop(&mut self) -> Option<V::Elem> {
330        if self.is_empty() {
331            return None;
332        }
333
334        self.vec.pop()
335    }
336
337    /// Remove a value at index, shifting all elements after it to the left.
338    ///
339    /// # Examples
340    ///
341    /// ```
342    /// use offset_vec::Offset;
343    ///
344    /// let mut vec = vec![0, 1, 2, 3, 4, 5];
345    /// let mut vec1 = vec.offset_mut(2);
346    ///
347    /// assert_eq!(vec1, [2, 3, 4, 5]);
348    /// assert_eq!(vec1.remove(1), 3);
349    /// assert_eq!(vec1, [2, 4, 5]);
350    ///
351    /// assert_eq!(vec, [0, 1, 2, 4, 5]);
352    /// ```
353    #[track_caller]
354    pub fn remove(&mut self, index: usize) -> V::Elem {
355        let len = self.len();
356        if index > len {
357            index_out_of_range(index, self.offset, len)
358        }
359        self.vec.remove(index + self.offset)
360    }
361
362    /// Insert a value before index, shifting all elements after it to the right.
363    ///
364    /// # Examples
365    ///
366    /// ```
367    /// use offset_vec::Offset;
368    ///
369    /// let mut vec = vec![0, 1, 2, 4, 5];
370    /// let mut vec1 = vec.offset_mut(2);
371    ///
372    /// assert_eq!(vec1, [2, 4, 5]);
373    /// vec1.insert(1, 3);
374    /// assert_eq!(vec1, [2, 3, 4, 5]);
375    /// vec1.insert(4, 6);
376    /// assert_eq!(vec1, [2, 3, 4, 5, 6]);
377    ///
378    /// assert_eq!(vec, [0, 1, 2, 3, 4, 5, 6]);
379    /// ```
380    #[track_caller]
381    pub fn insert(&mut self, index: usize, elem: V::Elem) {
382        let len = self.len();
383        if index > len {
384            index_out_of_range(index, self.offset, len)
385        }
386        self.vec.insert(index + self.offset, elem)
387    }
388
389    /// Truncate to length
390    ///
391    /// # Examples
392    ///
393    /// ```
394    /// use offset_vec::Offset;
395    ///
396    /// let mut vec = vec![0, 1, 2, 3, 4, 5];
397    /// let mut vec1 = vec.offset_mut(2);
398    ///
399    /// assert_eq!(vec1, [2, 3, 4, 5]);
400    ///
401    /// vec1.truncate(2);
402    ///
403    /// assert_eq!(vec1, [2, 3]);
404    /// assert_eq!(vec, [0, 1, 2, 3]);
405    /// ```
406    pub fn truncate(&mut self, len: usize) {
407        self.vec.truncate(len + self.offset);
408    }
409
410    /// Append and clear other collection
411    ///
412    /// # Examples
413    ///
414    /// ```
415    /// use offset_vec::Offset;
416    ///
417    /// let mut vec = vec![0, 1, 2, 3];
418    /// let mut vec1 = vec.offset_mut(2);
419    /// let mut other = vec![4, 5];
420    ///
421    /// assert_eq!(vec1, [2, 3]);
422    /// vec1.append(&mut other);
423    ///
424    /// assert_eq!(other, []);
425    /// assert_eq!(vec1, [2, 3, 4, 5]);
426    /// assert_eq!(vec, [0, 1, 2, 3, 4, 5]);
427    /// ```
428    pub fn append(&mut self, other: &mut V::Collection) {
429        self.vec.append(other);
430    }
431
432    /// Clear all elements (offset)
433    ///
434    /// # Examples
435    ///
436    /// ```
437    /// use offset_vec::Offset;
438    ///
439    /// let mut vec = vec![0, 1, 2, 3, 4];
440    /// let mut vec1 = vec.offset_mut(2);
441    ///
442    /// assert_eq!(vec1, [2, 3, 4]);
443    ///
444    /// vec1.clear();
445    ///
446    /// assert_eq!(vec1, []);
447    /// assert_eq!(vec, [0, 1]);
448    /// ```
449    pub fn clear(&mut self) {
450        self.vec.truncate(self.offset);
451    }
452
453    #[track_caller]
454    fn map_range<R: RangeBounds<usize>>(&self, range: R) -> Range<usize> {
455        let start = match range.start_bound() {
456            Bound::Included(&n) => n,
457            Bound::Excluded(&n) => n.checked_add(1).expect("start range overflow"),
458            Bound::Unbounded => 0,
459        };
460        let end = match range.end_bound() {
461            Bound::Included(&n) => n.checked_add(1).expect("end range overflow"),
462            Bound::Excluded(&n) => n,
463            Bound::Unbounded => self.len(),
464        };
465        if start > end {
466            #[cold]
467            #[track_caller]
468            #[inline(never)]
469            fn fail(index: usize, end: usize) -> ! {
470                panic!("range index starts at {index} but ends at {end}");
471            }
472            fail(start, end)
473        }
474        if end > self.len() {
475            #[cold]
476            #[track_caller]
477            #[inline(never)]
478            fn fail(index: usize, len: usize) -> ! {
479                panic!("range end index {index} out of range for slice of length {len}");
480            }
481            fail(end, self.len())
482        }
483        let offset = self.offset;
484        Range { start: start+offset, end: end+offset }
485    }
486
487    /// Drain range elements
488    ///
489    /// # Examples
490    ///
491    /// ```
492    /// use offset_vec::Offset;
493    ///
494    /// let mut vec = vec![0, 1, 2, 3, 4, 5, 6];
495    /// let mut vec1 = vec.offset_mut(2);
496    ///
497    /// assert_eq!(vec1, [2, 3, 4, 5, 6]);
498    ///
499    /// let drain = vec1.drain(2..4).collect::<Vec<_>>();
500    ///
501    /// assert_eq!(drain, [4, 5]);
502    /// assert_eq!(vec1, [2, 3, 6]);
503    /// assert_eq!(vec, [0, 1, 2, 3, 6]);
504    /// ```
505    #[track_caller]
506    pub fn drain<R: RangeBounds<usize>>(&mut self, range: R) -> V::Drain<'_> {
507        self.vec.drain(self.map_range(range))
508    }
509
510    /// Splits the collection into two at the given index.
511    ///
512    /// # Examples
513    ///
514    /// ```
515    /// use offset_vec::Offset;
516    ///
517    /// let mut vec = vec![0, 1, 2, 3, 4, 5, 6];
518    /// let mut vec1 = vec.offset_mut(2);
519    ///
520    /// assert_eq!(vec1, [2, 3, 4, 5, 6]);
521    ///
522    /// let other = vec1.split_off(3);
523    ///
524    /// assert_eq!(other, [5, 6]);
525    /// assert_eq!(vec1, [2, 3, 4]);
526    /// assert_eq!(vec, [0, 1, 2, 3, 4]);
527    /// ```
528    #[track_caller]
529    #[must_use = "use `.truncate()` if you don't need the other half"]
530    pub fn split_off(&mut self, at: usize) -> V::Collection {
531        let len = self.len();
532        if at > len {
533            index_out_of_range(at, self.offset, len)
534        }
535        self.vec.split_off(at + self.offset)
536    }
537
538    pub fn resize(&mut self, new_len: usize, value: V::Elem)
539    where V::Elem: Clone,
540    {
541        self.vec.resize(new_len+self.offset, value);
542    }
543
544    pub fn resize_with<F>(&mut self, new_len: usize, f: F)
545    where F: FnMut() -> V::Elem,
546    {
547        self.vec.resize_with(new_len+self.offset, f);
548    }
549
550    pub fn retain<F>(&mut self, mut f: F)
551    where F: FnMut(V::ElemRef<'_>) -> bool,
552    {
553        let i = self.vec.as_slice().transform_index(self.offset);
554
555        let mut i = 0..i;
556        self.vec.retain(|elem| {
557            i.next().is_some() || f(elem)
558        });
559    }
560}
561
562impl<V: VecLikeSolid> OffsetVec<V> {
563    pub fn retain_mut<F: FnMut(&mut V::Elem) -> bool>(&mut self, mut f: F) {
564        let mut i = 0..self.offset;
565        self.vec.retain_mut(|elem| {
566            i.next().is_some() || f(elem)
567        });
568    }
569
570    #[track_caller]
571    pub fn swap_remove(&mut self, index: usize) -> V::Elem {
572        let len = self.len();
573        if index > len {
574            index_out_of_range(index, self.offset, len)
575        }
576        self.vec.swap_remove(index + self.offset)
577    }
578
579    pub fn pop_if<F>(&mut self, predicate: F) -> Option<V::Elem>
580    where F: FnOnce(&mut V::Elem) -> bool,
581    {
582        if self.is_empty() {
583            return None;
584        }
585
586        self.vec.pop_if(predicate)
587    }
588}
589
590impl<V: VecLike<Slice = str>> OffsetVec<V> {
591    #[inline]
592    pub fn as_str(&self) -> &str {
593        self
594    }
595
596    #[inline]
597    pub fn as_mut_str(&mut self) -> &mut str {
598        self
599    }
600
601    pub fn push_str<'a>(&mut self, s: &'a str)
602    where V::Collection: Extend<&'a str>,
603    {
604        self.vec.as_mut_collection().extend(once(s));
605    }
606}
607
608#[cold]
609#[track_caller]
610#[inline(never)]
611fn index_out_of_range(index: usize, offset: usize, len: usize) -> ! {
612    panic!("offset index ({index} -> {}) out of length (is {len} -> {})",
613           index+offset,
614           len+offset);
615}