tiered_vector/
lib.rs

1//
2// Copyright (c) 2025 Nathan Fiedler
3//
4
5//! An implementation of tiered vectors as described in the paper **Tiered
6//! Vectors** by Goodrich and Kloss II, published in 1999.
7//!
8//! * DOI:10.1007/3-540-48447-7_21
9//!
10//! This implementation is based on the algorithms described in the 1998 version
11//! of the paper titled **Tiered Vector** by the same authors. In short, the
12//! structure consists of a dope vector that references one or more circular
13//! buffers in which all buffers are full, with the exception of the last buffer
14//! which may be partially filled.
15//!
16//! # Memory Usage
17//!
18//! An empty resizable vector is approximately 72 bytes in size, and while
19//! holding elements it will have a space overhead on the order of O(√N) as
20//! described in the paper. As elements are added the vector will grow by
21//! allocating additional data blocks. Likewise, as elements are removed from
22//! the vector, data blocks will be deallocated as they become empty.
23//!
24//! # Performance
25//!
26//! The performance and memory layout is as described in the paper: O(√N) space
27//! overhead, O(1) get and update operations, and O(√n) insert and remove.
28//!
29//! # Safety
30//!
31//! Because this data structure is allocating memory, copying bytes using raw
32//! pointers, and de-allocating memory as needed, there are many `unsafe` blocks
33//! throughout the code.
34
35use std::alloc::{Layout, alloc, dealloc, handle_alloc_error};
36use std::fmt;
37use std::ops::{Index, IndexMut};
38
39/// Tiered vector which maintains a collection of circular deques in order to
40/// efficiently support insert and remove from any location within the vector.
41pub struct Vector<T> {
42    /// each deque is of size l = 2^k
43    k: usize,
44    /// bit-mask to get the index into a circular deque
45    k_mask: usize,
46    /// the 'l' value (2^k) cached for performance
47    l: usize,
48    /// when count increases to this size, expand the vector
49    upper_limit: usize,
50    /// when count decreases to this size, compress the vector
51    lower_limit: usize,
52    /// number of elements in the vector
53    count: usize,
54    /// dope vector
55    index: Vec<CyclicArray<T>>,
56}
57
58impl<T> Vector<T> {
59    /// Return an empty vector with zero capacity.
60    pub fn new() -> Self {
61        // default l value of 4 like std::vec::Vec does for its initial
62        // allocation (its initial capacity is zero then becomes 4 then doubles
63        // with each expansion)
64        Self {
65            k: 2,
66            k_mask: 3,
67            l: 4,
68            upper_limit: 16,
69            lower_limit: 0,
70            count: 0,
71            index: vec![],
72        }
73    }
74
75    /// Double the capacity of this vector by combining its deques into new
76    /// deques of double the capacity.
77    fn expand(&mut self) {
78        let l_prime = 1 << (self.k + 1);
79        let old_index: Vec<CyclicArray<T>> = std::mem::take(&mut self.index);
80        let mut iter = old_index.into_iter();
81        while let Some(a) = iter.next() {
82            if let Some(b) = iter.next() {
83                self.index.push(CyclicArray::combine(a, b));
84            } else {
85                self.index.push(CyclicArray::from(l_prime, a));
86            }
87        }
88        self.k += 1;
89        self.k_mask = (1 << self.k) - 1;
90        self.l = 1 << self.k;
91        self.upper_limit = self.l * self.l;
92        self.lower_limit = self.upper_limit / 8;
93    }
94
95    /// Inserts an element at position `index` within the array, shifting some
96    /// elements to the right as needed.
97    pub fn insert(&mut self, index: usize, value: T) {
98        let len = self.count;
99        if index > len {
100            panic!("insertion index (is {index}) should be <= len (is {len})");
101        }
102        if len >= self.upper_limit {
103            self.expand();
104        }
105        if len >= self.capacity() {
106            self.index.push(CyclicArray::<T>::new(self.l));
107        }
108        let sub = index >> self.k;
109        let end = len >> self.k;
110        let r_prime = index & self.k_mask;
111        if sub < end {
112            // push-pop phase
113            let mut head = self.index[sub].pop_back().unwrap();
114            for i in (sub + 1)..end {
115                let tail = self.index[i].pop_back().unwrap();
116                self.index[i].push_front(head);
117                head = tail;
118            }
119            self.index[end].push_front(head);
120        }
121        // shift phase
122        self.index[sub].insert(r_prime, value);
123        self.count += 1;
124    }
125
126    /// Appends an element to the back of a collection.
127    ///
128    /// # Panics
129    ///
130    /// Panics if a new block is allocated that would exceed `isize::MAX` _bytes_.
131    ///
132    /// # Time complexity
133    ///
134    /// O(√N) in the worst case.
135    pub fn push(&mut self, value: T) {
136        self.insert(self.count, value);
137    }
138
139    /// Appends an element if there is sufficient spare capacity, otherwise an
140    /// error is returned with the element.
141    ///
142    /// # Time complexity
143    ///
144    /// O(√N) in the worst case.
145    pub fn push_within_capacity(&mut self, value: T) -> Result<(), T> {
146        if self.capacity() <= self.count {
147            Err(value)
148        } else {
149            self.push(value);
150            Ok(())
151        }
152    }
153
154    /// Retrieve a reference to the element at the given offset.
155    ///
156    /// # Time complexity
157    ///
158    /// Constant time.
159    pub fn get(&self, index: usize) -> Option<&T> {
160        if index >= self.count {
161            None
162        } else {
163            let sub = index >> self.k;
164            let r_prime = index & self.k_mask;
165            self.index[sub].get(r_prime)
166        }
167    }
168
169    /// Returns a mutable reference to an element.
170    ///
171    /// # Time complexity
172    ///
173    /// Constant time.
174    pub fn get_mut(&mut self, index: usize) -> Option<&mut T> {
175        if index >= self.count {
176            None
177        } else {
178            let sub = index >> self.k;
179            let r_prime = index & self.k_mask;
180            self.index[sub].get_mut(r_prime)
181        }
182    }
183
184    /// Shrink the capacity of this vector by splitting its deques into new
185    /// deques of half the capacity.
186    fn compress(&mut self) {
187        let old_index: Vec<CyclicArray<T>> = std::mem::take(&mut self.index);
188        for old_deque in old_index.into_iter() {
189            let (a, b) = old_deque.split();
190            self.index.push(a);
191            self.index.push(b);
192        }
193        self.k -= 1;
194        self.k_mask = (1 << self.k) - 1;
195        self.l = 1 << self.k;
196        self.upper_limit = self.l * self.l;
197        self.lower_limit = self.upper_limit / 8;
198    }
199
200    /// Removes an element from position `index` within the array, shifting some
201    /// elements to the left as needed to close the gap.
202    ///
203    /// # Time complexity
204    ///
205    /// O(√N) in the worst case.
206    pub fn remove(&mut self, index: usize) -> T {
207        let len = self.count;
208        if index > len {
209            panic!("removal index (is {index}) should be <= len (is {len})");
210        }
211        // avoid compressing to deques smaller than 4
212        if len < self.lower_limit && self.k > 2 {
213            self.compress();
214        }
215        let sub = index >> self.k;
216        let end = (len - 1) >> self.k;
217        let r_prime = index & self.k_mask;
218        // shift phase
219        let ret = self.index[sub].remove(r_prime);
220        if sub < end {
221            // push-pop phase
222            let mut tail = self.index[end].pop_front().unwrap();
223            for i in (sub + 1..end).rev() {
224                let head = self.index[i].pop_front().unwrap();
225                self.index[i].push_back(tail);
226                tail = head;
227            }
228            self.index[sub].push_back(tail);
229        }
230        if self.index[end].is_empty() {
231            // prune circular arrays as they become empty
232            self.index.pop();
233        }
234        self.count -= 1;
235        ret
236    }
237
238    /// Removes the last element from the vector and returns it, or `None` if the
239    /// vector is empty.
240    ///
241    /// # Time complexity
242    ///
243    /// O(√N) in the worst case.
244    pub fn pop(&mut self) -> Option<T> {
245        if self.count > 0 {
246            Some(self.remove(self.count - 1))
247        } else {
248            None
249        }
250    }
251
252    /// Removes and returns the last element from a vector if the predicate
253    /// returns true, or `None`` if the predicate returns `false`` or the vector
254    /// is empty (the predicate will not be called in that case).
255    ///
256    /// # Time complexity
257    ///
258    /// O(√N) in the worst case.
259    pub fn pop_if(&mut self, predicate: impl FnOnce(&mut T) -> bool) -> Option<T> {
260        if self.count == 0 {
261            None
262        } else if let Some(last) = self.get_mut(self.count - 1) {
263            if predicate(last) { self.pop() } else { None }
264        } else {
265            None
266        }
267    }
268
269    // Returns an iterator over the vector.
270    //
271    // The iterator yields all items from start to end.
272    pub fn iter(&self) -> VectorIter<'_, T> {
273        VectorIter {
274            array: self,
275            index: 0,
276        }
277    }
278
279    /// Return the number of elements in the vector.
280    ///
281    /// # Time complexity
282    ///
283    /// Constant time.
284    pub fn len(&self) -> usize {
285        self.count
286    }
287
288    /// Returns the total number of elements the vector can hold without
289    /// reallocating.
290    ///
291    /// # Time complexity
292    ///
293    /// Constant time.
294    pub fn capacity(&self) -> usize {
295        (1 << self.k) * self.index.len()
296    }
297
298    /// Returns true if the array has a length of 0.
299    ///
300    /// # Time complexity
301    ///
302    /// Constant time.
303    pub fn is_empty(&self) -> bool {
304        self.count == 0
305    }
306
307    /// Clears the vector, removing all values and deallocating all blocks.
308    ///
309    /// # Time complexity
310    ///
311    /// O(n) if elements are droppable, otherwise O(√N)
312    pub fn clear(&mut self) {
313        self.index.clear();
314        self.count = 0;
315        self.k = 2;
316        self.k_mask = 3;
317        self.l = 1 << self.k;
318        self.upper_limit = self.l * self.l;
319        self.lower_limit = self.upper_limit / 8;
320    }
321}
322
323impl<T> Default for Vector<T> {
324    fn default() -> Self {
325        Self::new()
326    }
327}
328
329impl<T> fmt::Display for Vector<T> {
330    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
331        write!(
332            f,
333            "Vector(k: {}, count: {}, dope: {})",
334            self.k,
335            self.count,
336            self.index.len(),
337        )
338    }
339}
340
341impl<T> Index<usize> for Vector<T> {
342    type Output = T;
343
344    fn index(&self, index: usize) -> &Self::Output {
345        let Some(item) = self.get(index) else {
346            panic!("index out of bounds: {}", index);
347        };
348        item
349    }
350}
351
352impl<T> IndexMut<usize> for Vector<T> {
353    fn index_mut(&mut self, index: usize) -> &mut Self::Output {
354        let Some(item) = self.get_mut(index) else {
355            panic!("index out of bounds: {}", index);
356        };
357        item
358    }
359}
360
361impl<A> FromIterator<A> for Vector<A> {
362    fn from_iter<T: IntoIterator<Item = A>>(iter: T) -> Self {
363        let mut arr: Vector<A> = Vector::new();
364        for value in iter {
365            arr.push(value)
366        }
367        arr
368    }
369}
370
371/// Immutable array iterator.
372pub struct VectorIter<'a, T> {
373    array: &'a Vector<T>,
374    index: usize,
375}
376
377impl<'a, T> Iterator for VectorIter<'a, T> {
378    type Item = &'a T;
379
380    fn next(&mut self) -> Option<Self::Item> {
381        let value = self.array.get(self.index);
382        self.index += 1;
383        value
384    }
385}
386
387impl<T> IntoIterator for Vector<T> {
388    type Item = T;
389    type IntoIter = VectorIntoIter<Self::Item>;
390
391    fn into_iter(self) -> Self::IntoIter {
392        let mut me = std::mem::ManuallyDrop::new(self);
393        let index = std::mem::take(&mut me.index);
394        VectorIntoIter {
395            count: me.count,
396            index,
397        }
398    }
399}
400
401/// An iterator that moves out of a tiered vector.
402pub struct VectorIntoIter<T> {
403    /// number of remaining elements
404    count: usize,
405    /// index of circular deques
406    index: Vec<CyclicArray<T>>,
407}
408
409impl<T> Iterator for VectorIntoIter<T> {
410    type Item = T;
411
412    fn next(&mut self) -> Option<Self::Item> {
413        if self.count > 0 {
414            let ret = self.index[0].pop_front();
415            self.count -= 1;
416            if self.index[0].is_empty() {
417                self.index.remove(0);
418            }
419            ret
420        } else {
421            None
422        }
423    }
424}
425
426/// Basic circular buffer, or what Goodrich and Kloss call a circular deque.
427///
428/// This implementation allows push and pop from both ends of the buffer and
429/// supports insert and remove from arbitrary offsets.
430///
431/// Unlike the `VecDeque` in the standard library, this array has a fixed size
432/// and will panic if a push is performed while the array is already full.
433pub struct CyclicArray<T> {
434    /// allocated buffer of size `capacity`
435    buffer: *mut T,
436    /// number of slots allocated in the buffer
437    capacity: usize,
438    /// offset of the first entry
439    head: usize,
440    /// number of elements
441    count: usize,
442}
443
444impl<T> CyclicArray<T> {
445    /// Construct a new cyclic array with the given capacity.
446    pub fn new(capacity: usize) -> Self {
447        let buffer = if capacity == 0 {
448            std::ptr::null_mut::<T>()
449        } else {
450            let layout = Layout::array::<T>(capacity).expect("unexpected overflow");
451            unsafe {
452                let ptr = alloc(layout).cast::<T>();
453                if ptr.is_null() {
454                    handle_alloc_error(layout);
455                }
456                ptr
457            }
458        };
459        Self {
460            buffer,
461            capacity,
462            head: 0,
463            count: 0,
464        }
465    }
466
467    /// Free the buffer for this cyclic array without dropping the elements.
468    fn dealloc(&mut self) {
469        // apparently this has no effect if capacity is zero
470        let layout = Layout::array::<T>(self.capacity).expect("unexpected overflow");
471        unsafe {
472            dealloc(self.buffer as *mut u8, layout);
473        }
474    }
475
476    /// Take the elements from the two other cyclic arrays into a new cyclic
477    /// array with the combined capacity.
478    pub fn combine(a: CyclicArray<T>, b: CyclicArray<T>) -> Self {
479        let mut this: CyclicArray<T> = CyclicArray::new(a.capacity + b.capacity);
480        let mut this_pos = 0;
481        let their_a = std::mem::ManuallyDrop::new(a);
482        let their_b = std::mem::ManuallyDrop::new(b);
483        for mut other in [their_a, their_b] {
484            if other.head + other.count > other.capacity {
485                // data wraps around, copy as two blocks
486                let src = unsafe { other.buffer.add(other.head) };
487                let dst = unsafe { this.buffer.add(this_pos) };
488                let count_1 = other.capacity - other.head;
489                unsafe { std::ptr::copy(src, dst, count_1) }
490                this_pos += count_1;
491                let dst = unsafe { this.buffer.add(this_pos) };
492                let count_2 = other.count - count_1;
493                unsafe { std::ptr::copy(other.buffer, dst, count_2) }
494                this_pos += count_2;
495            } else {
496                // data is contiguous, copy as one block
497                let src = unsafe { other.buffer.add(other.head) };
498                let dst = unsafe { this.buffer.add(this_pos) };
499                unsafe { std::ptr::copy(src, dst, other.count) }
500                this_pos += other.count;
501            }
502            other.dealloc();
503            this.count += other.count;
504        }
505        this
506    }
507
508    /// Take the elements from the other cyclic array into a new cyclic array
509    /// with the given capacity.
510    pub fn from(capacity: usize, other: CyclicArray<T>) -> Self {
511        assert!(capacity > other.count, "capacity cannot be less than count");
512        let layout = Layout::array::<T>(capacity).expect("unexpected overflow");
513        let buffer = unsafe {
514            let ptr = alloc(layout).cast::<T>();
515            if ptr.is_null() {
516                handle_alloc_error(layout);
517            }
518            ptr
519        };
520        let mut them = std::mem::ManuallyDrop::new(other);
521        if them.head + them.count > them.capacity {
522            // data wraps around, copy as two blocks
523            let src = unsafe { them.buffer.add(them.head) };
524            let count_1 = them.capacity - them.head;
525            unsafe { std::ptr::copy(src, buffer, count_1) }
526            let dst = unsafe { buffer.add(count_1) };
527            let count_2 = them.count - count_1;
528            unsafe { std::ptr::copy(them.buffer, dst, count_2) }
529        } else {
530            // data is contiguous, copy as one block
531            let src = unsafe { them.buffer.add(them.head) };
532            unsafe { std::ptr::copy(src, buffer, them.count) }
533        }
534        them.dealloc();
535        Self {
536            buffer,
537            capacity,
538            head: 0,
539            count: them.count,
540        }
541    }
542
543    /// Split this cyclic buffer into two equal sized buffers.
544    ///
545    /// The second buffer may be empty if all elements fit within the first
546    /// buffer.
547    pub fn split(self) -> (CyclicArray<T>, CyclicArray<T>) {
548        assert!(
549            self.capacity.is_multiple_of(2),
550            "capacity must be an even number"
551        );
552        let half = self.capacity / 2;
553        let mut me = std::mem::ManuallyDrop::new(self);
554        let mut a: CyclicArray<T> = CyclicArray::new(half);
555        let mut b: CyclicArray<T> = CyclicArray::new(half);
556        let mut remaining = me.count;
557        for other in [&mut a, &mut b] {
558            let mut other_pos = 0;
559            while remaining > 0 && !other.is_full() {
560                let want_to_copy = if me.head + remaining > me.capacity {
561                    me.capacity - me.head
562                } else {
563                    remaining
564                };
565                let can_fit = other.capacity - other.count;
566                let to_copy = if want_to_copy > can_fit {
567                    can_fit
568                } else {
569                    want_to_copy
570                };
571                let src = unsafe { me.buffer.add(me.head) };
572                let dst = unsafe { other.buffer.add(other_pos) };
573                unsafe { std::ptr::copy(src, dst, to_copy) };
574                other_pos += to_copy;
575                other.count += to_copy;
576                me.head = me.physical_add(to_copy);
577                remaining -= to_copy;
578            }
579        }
580        me.dealloc();
581        (a, b)
582    }
583
584    /// Appends an element to the back of the cyclic array.
585    ///
586    /// # Panic
587    ///
588    /// Panics if the buffer is already full.
589    pub fn push_back(&mut self, value: T) {
590        if self.count == self.capacity {
591            panic!("cyclic array is full")
592        }
593        let off = self.physical_add(self.count);
594        unsafe { std::ptr::write(self.buffer.add(off), value) }
595        self.count += 1;
596    }
597
598    /// Prepends an element to the front of the cyclic array.
599    ///
600    /// # Panic
601    ///
602    /// Panics if the buffer is already full.
603    pub fn push_front(&mut self, value: T) {
604        if self.count == self.capacity {
605            panic!("cyclic array is full")
606        }
607        self.head = self.physical_sub(1);
608        unsafe { std::ptr::write(self.buffer.add(self.head), value) }
609        self.count += 1;
610    }
611
612    /// Removes the last element and returns it, or `None` if the cyclic array
613    /// is empty.
614    pub fn pop_back(&mut self) -> Option<T> {
615        if self.count == 0 {
616            None
617        } else {
618            self.count -= 1;
619            let off = self.physical_add(self.count);
620            unsafe { Some(std::ptr::read(self.buffer.add(off))) }
621        }
622    }
623
624    /// Removes the first element and returns it, or `None` if the cyclic array
625    /// is empty.
626    pub fn pop_front(&mut self) -> Option<T> {
627        if self.count == 0 {
628            None
629        } else {
630            let old_head = self.head;
631            self.head = self.physical_add(1);
632            self.count -= 1;
633            unsafe { Some(std::ptr::read(self.buffer.add(old_head))) }
634        }
635    }
636
637    /// Inserts an element at position `index` within the array, possibly
638    /// shifting some elements to the left or the right as needed.
639    pub fn insert(&mut self, index: usize, value: T) {
640        let len = self.count;
641        if index > len {
642            panic!("insertion index (is {index}) should be <= len (is {len})");
643        }
644        if len == self.capacity {
645            panic!("cyclic array is full")
646        }
647        //
648        // Some free space exists in the array, either on the left, the right,
649        // the middle, at both ends, or the entire array is empty. Regardless,
650        // there are two cases, shift some elements to the left or to the right.
651        //
652        let mut r_prime = self.physical_add(index);
653        if len > 0 && index < len {
654            // need to make space for the new element
655            if self.head == 0 || r_prime < self.head {
656                // Slide all elements in S,sub of rank greater than or equal to
657                // r’ and less than (|S,sub| — r’) mod l to the right by one
658                let src = unsafe { self.buffer.add(r_prime) };
659                let dst = unsafe { self.buffer.add(r_prime + 1) };
660                let count = self.count - index;
661                unsafe { std::ptr::copy(src, dst, count) }
662            } else {
663                // Slide all elements in S,sub of rank less than r’ and greater
664                // than or equal to h,sub to the left by one
665                let src = unsafe { self.buffer.add(self.head) };
666                let count = r_prime - self.head;
667                self.head = self.physical_sub(1);
668                let dst = unsafe { self.buffer.add(self.head) };
669                unsafe { std::ptr::copy(src, dst, count) }
670                r_prime -= 1;
671            }
672        }
673        unsafe { std::ptr::write(self.buffer.add(r_prime), value) }
674        self.count += 1;
675    }
676
677    /// Removes and returns the element at position `index` within the array,
678    /// shifting some elements to the left or to the right.
679    pub fn remove(&mut self, index: usize) -> T {
680        let len = self.count;
681        if index >= len {
682            panic!("removal index (is {index}) should be < len (is {len})");
683        }
684        let r_prime = self.physical_add(index);
685        let ret = unsafe { std::ptr::read(self.buffer.add(r_prime)) };
686        if index < (len - 1) {
687            // need to slide elements to fill the new gap
688            if self.head == 0 || r_prime < self.head {
689                // Slide all elements in S,sub of rank r'+1 to h,sub + |S,sub| to
690                // the left by one
691                let src = unsafe { self.buffer.add(r_prime + 1) };
692                let dst = unsafe { self.buffer.add(r_prime) };
693                let count = self.count - index - 1;
694                unsafe { std::ptr::copy(src, dst, count) }
695            } else {
696                // Slide all elements in S,sub of rank greater than or equal to
697                // h,sub and less than r' to the right by one
698                let src = unsafe { self.buffer.add(self.head) };
699                let count = r_prime - self.head;
700                self.head = self.physical_add(1);
701                let dst = unsafe { self.buffer.add(self.head) };
702                unsafe { std::ptr::copy(src, dst, count) }
703            }
704        }
705        self.count -= 1;
706        ret
707    }
708
709    /// Provides a reference to the element at the given index.
710    pub fn get(&self, index: usize) -> Option<&T> {
711        if index < self.count {
712            let idx = self.physical_add(index);
713            unsafe { Some(&*self.buffer.add(idx)) }
714        } else {
715            None
716        }
717    }
718
719    /// Returns a mutable reference to an element.
720    pub fn get_mut(&mut self, index: usize) -> Option<&mut T> {
721        if index < self.count {
722            let idx = self.physical_add(index);
723            unsafe { (self.buffer.add(idx)).as_mut() }
724        } else {
725            None
726        }
727    }
728
729    /// Clears the cyclic array, removing and dropping all values.
730    pub fn clear(&mut self) {
731        use std::ptr::{drop_in_place, slice_from_raw_parts_mut};
732
733        if self.count > 0 && std::mem::needs_drop::<T>() {
734            let first_slot = self.physical_add(0);
735            let last_slot = self.physical_add(self.count);
736            if first_slot < last_slot {
737                // elements are in one contiguous block
738                unsafe {
739                    drop_in_place(slice_from_raw_parts_mut(
740                        self.buffer.add(first_slot),
741                        last_slot - first_slot,
742                    ));
743                }
744            } else {
745                // elements wrap around the end of the buffer
746                unsafe {
747                    drop_in_place(slice_from_raw_parts_mut(
748                        self.buffer.add(first_slot),
749                        self.capacity - first_slot,
750                    ));
751                    // check if first and last are at the start of the array
752                    if first_slot != last_slot || first_slot != 0 {
753                        drop_in_place(slice_from_raw_parts_mut(self.buffer, last_slot));
754                    }
755                }
756            }
757        }
758        self.head = 0;
759        self.count = 0;
760    }
761
762    /// Return the number of elements in the array.
763    pub fn len(&self) -> usize {
764        self.count
765    }
766
767    /// Returns the total number of elements the cyclic array can hold.
768    pub fn capacity(&self) -> usize {
769        self.capacity
770    }
771
772    /// Returns true if the array has a length of 0.
773    pub fn is_empty(&self) -> bool {
774        self.count == 0
775    }
776
777    /// Returns true if the array has a length equal to its capacity.
778    pub fn is_full(&self) -> bool {
779        self.count == self.capacity
780    }
781
782    /// Perform a wrapping addition relative to the head of the array and
783    /// convert the logical offset to the physical offset within the array.
784    fn physical_add(&self, addend: usize) -> usize {
785        let logical_index = self.head.wrapping_add(addend);
786        if logical_index >= self.capacity {
787            logical_index - self.capacity
788        } else {
789            logical_index
790        }
791    }
792
793    /// Perform a wrapping subtraction relative to the head of the array and
794    /// convert the logical offset to the physical offset within the array.
795    fn physical_sub(&self, subtrahend: usize) -> usize {
796        let logical_index = self
797            .head
798            .wrapping_sub(subtrahend)
799            .wrapping_add(self.capacity);
800        if logical_index >= self.capacity {
801            logical_index - self.capacity
802        } else {
803            logical_index
804        }
805    }
806}
807
808impl<T> Default for CyclicArray<T> {
809    fn default() -> Self {
810        Self::new(0)
811    }
812}
813
814impl<T> fmt::Display for CyclicArray<T> {
815    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
816        write!(
817            f,
818            "CyclicArray(capacity: {}, head: {}, count: {})",
819            self.capacity, self.head, self.count,
820        )
821    }
822}
823
824impl<T> Index<usize> for CyclicArray<T> {
825    type Output = T;
826
827    fn index(&self, index: usize) -> &Self::Output {
828        let Some(item) = self.get(index) else {
829            panic!("index out of bounds: {}", index);
830        };
831        item
832    }
833}
834
835impl<T> IndexMut<usize> for CyclicArray<T> {
836    fn index_mut(&mut self, index: usize) -> &mut Self::Output {
837        let Some(item) = self.get_mut(index) else {
838            panic!("index out of bounds: {}", index);
839        };
840        item
841    }
842}
843
844impl<T> Drop for CyclicArray<T> {
845    fn drop(&mut self) {
846        self.clear();
847        self.dealloc();
848    }
849}
850
851#[cfg(test)]
852mod tests {
853    use super::*;
854
855    #[test]
856    fn test_vector_insert_head() {
857        let mut sut = Vector::<usize>::new();
858        assert!(sut.is_empty());
859        for value in (1..=16).rev() {
860            sut.insert(0, value);
861        }
862        assert!(!sut.is_empty());
863        for (index, value) in (1..=16).enumerate() {
864            assert_eq!(sut[index], value);
865        }
866    }
867
868    #[test]
869    fn test_vector_push_and_clear() {
870        let mut sut = Vector::<usize>::new();
871        assert!(sut.is_empty());
872        for value in 0..64 {
873            sut.push(value);
874        }
875        assert!(!sut.is_empty());
876        assert_eq!(sut.len(), 64);
877        assert_eq!(sut.capacity(), 64);
878        for value in 0..64 {
879            assert_eq!(sut[value], value);
880        }
881        sut.clear();
882        assert!(sut.is_empty());
883        assert_eq!(sut.len(), 0);
884        assert_eq!(sut.capacity(), 0);
885    }
886
887    #[test]
888    fn test_vector_get_mut() {
889        let mut sut = Vector::<usize>::new();
890        for value in 0..4 {
891            sut.push(value);
892        }
893        if let Some(value) = sut.get_mut(1) {
894            *value = 11;
895        } else {
896            panic!("get_mut() returned None")
897        }
898        sut[2] = 12;
899        assert_eq!(sut.len(), 4);
900        assert_eq!(sut[0], 0);
901        assert_eq!(sut[1], 11);
902        assert_eq!(sut[2], 12);
903        assert_eq!(sut[3], 3);
904    }
905
906    #[test]
907    fn test_vector_insert_expand() {
908        let mut sut = Vector::<usize>::new();
909        assert!(sut.is_empty());
910        for value in (1..=130).rev() {
911            sut.insert(0, value);
912        }
913        assert!(!sut.is_empty());
914        assert_eq!(sut.len(), 130);
915        assert_eq!(sut.capacity(), 144);
916        for value in 0..130 {
917            assert_eq!(sut[value], value + 1);
918        }
919    }
920
921    #[test]
922    fn test_vector_push_many() {
923        let mut sut = Vector::<usize>::new();
924        assert!(sut.is_empty());
925        for value in 0..100_000 {
926            sut.push(value);
927        }
928        assert!(!sut.is_empty());
929        assert_eq!(sut.len(), 100_000);
930        assert_eq!(sut.capacity(), 100352);
931        for value in 0..100_000 {
932            assert_eq!(sut[value], value);
933        }
934    }
935
936    #[test]
937    fn test_vector_push_within_capacity() {
938        // empty array has no allocated space
939        let mut sut = Vector::<u32>::new();
940        assert_eq!(sut.push_within_capacity(101), Err(101));
941        sut.push(1);
942        sut.push(2);
943        assert_eq!(sut.push_within_capacity(3), Ok(()));
944        assert_eq!(sut.push_within_capacity(4), Ok(()));
945        assert_eq!(sut.push_within_capacity(5), Err(5));
946    }
947
948    #[test]
949    fn test_vector_remove_small() {
950        let mut sut = Vector::<usize>::new();
951        assert!(sut.is_empty());
952        assert_eq!(sut.len(), 0);
953        for value in 0..15 {
954            sut.push(value);
955        }
956        assert!(!sut.is_empty());
957        assert_eq!(sut.len(), 15);
958        for value in 0..15 {
959            assert_eq!(sut.remove(0), value);
960        }
961        assert!(sut.is_empty());
962        assert_eq!(sut.len(), 0);
963        assert_eq!(sut.capacity(), 0);
964    }
965
966    #[test]
967    fn test_vector_remove_medium() {
968        let mut sut = Vector::<usize>::new();
969        assert!(sut.is_empty());
970        assert_eq!(sut.len(), 0);
971        assert_eq!(sut.capacity(), 0);
972        for value in 0..2048 {
973            sut.push(value);
974        }
975        assert!(!sut.is_empty());
976        assert_eq!(sut.len(), 2048);
977        assert_eq!(sut.capacity(), 2048);
978        for value in 0..2048 {
979            assert_eq!(sut.remove(0), value);
980        }
981        assert!(sut.is_empty());
982        assert_eq!(sut.len(), 0);
983        assert_eq!(sut.capacity(), 0);
984    }
985
986    #[test]
987    fn test_vector_expand_and_compress() {
988        // add enough to cause multiple expansions
989        let mut sut = Vector::<usize>::new();
990        for value in 0..1024 {
991            sut.push(value);
992        }
993        assert_eq!(sut.len(), 1024);
994        assert_eq!(sut.capacity(), 1024);
995        // remove enough to cause multiple compressions
996        for _ in 0..960 {
997            sut.pop();
998        }
999        // ensure the correct elements remain
1000        assert_eq!(sut.len(), 64);
1001        assert_eq!(sut.capacity(), 64);
1002        for value in 0..64 {
1003            assert_eq!(sut[value], value);
1004        }
1005    }
1006
1007    #[test]
1008    fn test_vector_pop_small() {
1009        let mut sut = Vector::<usize>::new();
1010        assert!(sut.is_empty());
1011        assert_eq!(sut.len(), 0);
1012        for value in 0..15 {
1013            sut.push(value);
1014        }
1015        assert!(!sut.is_empty());
1016        assert_eq!(sut.len(), 15);
1017        for value in (0..15).rev() {
1018            assert_eq!(sut.pop(), Some(value));
1019        }
1020        assert!(sut.is_empty());
1021        assert_eq!(sut.len(), 0);
1022        assert_eq!(sut.capacity(), 0);
1023    }
1024
1025    #[test]
1026    fn test_vector_pop_if() {
1027        let mut sut = Vector::<u32>::new();
1028        assert!(sut.pop_if(|_| panic!("should not be called")).is_none());
1029        for value in 0..10 {
1030            sut.push(value);
1031        }
1032        assert!(sut.pop_if(|_| false).is_none());
1033        let maybe = sut.pop_if(|v| *v == 9);
1034        assert_eq!(maybe.unwrap(), 9);
1035        assert!(sut.pop_if(|v| *v == 9).is_none());
1036    }
1037
1038    #[test]
1039    fn test_vector_iter() {
1040        let mut sut = Vector::<usize>::new();
1041        for value in 0..1000 {
1042            sut.push(value);
1043        }
1044        assert_eq!(sut.len(), 1000);
1045        for (index, value) in sut.iter().enumerate() {
1046            assert_eq!(sut[index], *value);
1047        }
1048    }
1049
1050    #[test]
1051    fn test_vector_from_iterator() {
1052        let mut inputs: Vec<i32> = Vec::new();
1053        for value in 0..10_000 {
1054            inputs.push(value);
1055        }
1056        let sut: Vector<i32> = inputs.into_iter().collect();
1057        assert_eq!(sut.len(), 10_000);
1058        for idx in 0..10_000i32 {
1059            let maybe = sut.get(idx as usize);
1060            assert!(maybe.is_some(), "{idx} is none");
1061            let actual = maybe.unwrap();
1062            assert_eq!(idx, *actual);
1063        }
1064    }
1065
1066    #[test]
1067    fn test_vector_into_iterator_drop_empty() {
1068        let sut: Vector<String> = Vector::new();
1069        assert_eq!(sut.into_iter().count(), 0);
1070    }
1071
1072    #[test]
1073    fn test_vector_into_iterator_ints_done() {
1074        let mut sut = Vector::<usize>::new();
1075        for value in 0..1024 {
1076            sut.push(value);
1077        }
1078        for (idx, elem) in sut.into_iter().enumerate() {
1079            assert_eq!(idx, elem);
1080        }
1081        // sut.len(); // error: ownership of sut was moved
1082    }
1083
1084    #[test]
1085    fn test_vector_remove_insert_basic() {
1086        let mut sut = Vector::<usize>::new();
1087        for value in 1..=16 {
1088            sut.push(value);
1089        }
1090        let value = sut.remove(3);
1091        sut.insert(7, value);
1092        let mut sorted: Vec<usize> = sut.into_iter().collect();
1093        sorted.sort();
1094        for (index, value) in (1..=16).enumerate() {
1095            assert_eq!(sorted[index], value);
1096        }
1097    }
1098
1099    #[test]
1100    fn test_vector_random_insert_remove() {
1101        // trade-off of exhaustive randomized testing and running time
1102        let mut sut = Vector::<usize>::new();
1103        let size = 100_000;
1104        for value in 1..=size {
1105            sut.push(value);
1106        }
1107        for _ in 0..200_000 {
1108            let from = rand::random_range(0..size);
1109            let to = rand::random_range(0..size - 1);
1110            let value = sut.remove(from);
1111            sut.insert(to, value);
1112        }
1113        let mut sorted: Vec<usize> = sut.into_iter().collect();
1114        sorted.sort();
1115        for (idx, value) in (1..=size).enumerate() {
1116            assert_eq!(sorted[idx], value);
1117        }
1118    }
1119
1120    #[test]
1121    fn test_vector_push_pop_strings() {
1122        let mut array: Vector<String> = Vector::new();
1123        for _ in 0..1024 {
1124            let value = ulid::Ulid::new().to_string();
1125            array.push(value);
1126        }
1127        assert_eq!(array.len(), 1024);
1128        while let Some(s) = array.pop() {
1129            assert!(!s.is_empty());
1130        }
1131    }
1132
1133    #[test]
1134    fn test_cyclic_array_zero_capacity() {
1135        let sut = CyclicArray::<usize>::new(0);
1136        assert_eq!(sut.len(), 0);
1137        assert_eq!(sut.capacity(), 0);
1138        assert!(sut.is_empty());
1139        assert!(sut.is_full());
1140    }
1141
1142    #[test]
1143    #[should_panic(expected = "cyclic array is full")]
1144    fn test_cyclic_array_zero_push_panics() {
1145        let mut sut = CyclicArray::<usize>::new(0);
1146        sut.push_back(101);
1147    }
1148
1149    #[test]
1150    fn test_cyclic_array_forward() {
1151        let mut sut = CyclicArray::<usize>::new(10);
1152        assert_eq!(sut.len(), 0);
1153        assert_eq!(sut.capacity(), 10);
1154        assert!(sut.is_empty());
1155        assert!(!sut.is_full());
1156
1157        // add until full
1158        for value in 0..sut.capacity() {
1159            sut.push_back(value);
1160        }
1161        assert_eq!(sut.len(), 10);
1162        assert_eq!(sut.capacity(), 10);
1163        assert!(!sut.is_empty());
1164        assert!(sut.is_full());
1165
1166        assert_eq!(sut.get(1), Some(&1));
1167        assert_eq!(sut[1], 1);
1168        assert_eq!(sut.get(3), Some(&3));
1169        assert_eq!(sut[3], 3);
1170        assert_eq!(sut.get(6), Some(&6));
1171        assert_eq!(sut[6], 6);
1172        assert_eq!(sut.get(9), Some(&9));
1173        assert_eq!(sut[9], 9);
1174        assert_eq!(sut.get(10), None);
1175
1176        // remove until empty
1177        for index in 0..10 {
1178            let maybe = sut.pop_front();
1179            assert!(maybe.is_some());
1180            let value = maybe.unwrap();
1181            assert_eq!(value, index);
1182        }
1183        assert_eq!(sut.len(), 0);
1184        assert_eq!(sut.capacity(), 10);
1185        assert!(sut.is_empty());
1186        assert!(!sut.is_full());
1187    }
1188
1189    #[test]
1190    fn test_cyclic_array_backward() {
1191        let mut sut = CyclicArray::<usize>::new(10);
1192        assert_eq!(sut.len(), 0);
1193        assert_eq!(sut.capacity(), 10);
1194        assert!(sut.is_empty());
1195        assert!(!sut.is_full());
1196
1197        // add until full
1198        for value in 0..sut.capacity() {
1199            sut.push_front(value);
1200        }
1201        assert_eq!(sut.len(), 10);
1202        assert_eq!(sut.capacity(), 10);
1203        assert!(!sut.is_empty());
1204        assert!(sut.is_full());
1205
1206        // everything is backwards
1207        assert_eq!(sut.get(1), Some(&8));
1208        assert_eq!(sut[1], 8);
1209        assert_eq!(sut.get(3), Some(&6));
1210        assert_eq!(sut[3], 6);
1211        assert_eq!(sut.get(6), Some(&3));
1212        assert_eq!(sut[6], 3);
1213        assert_eq!(sut.get(9), Some(&0));
1214        assert_eq!(sut[9], 0);
1215        assert_eq!(sut.get(10), None);
1216
1217        // remove until empty
1218        for index in 0..10 {
1219            let maybe = sut.pop_back();
1220            assert!(maybe.is_some());
1221            let value = maybe.unwrap();
1222            assert_eq!(value, index);
1223        }
1224        assert_eq!(sut.len(), 0);
1225        assert_eq!(sut.capacity(), 10);
1226        assert!(sut.is_empty());
1227        assert!(!sut.is_full());
1228    }
1229
1230    #[test]
1231    #[should_panic(expected = "index out of bounds:")]
1232    fn test_cyclic_array_index_out_of_bounds() {
1233        let mut sut = CyclicArray::<usize>::new(10);
1234        sut.push_back(10);
1235        sut.push_back(20);
1236        let _ = sut[2];
1237    }
1238
1239    #[test]
1240    fn test_cyclic_array_clear_and_reuse() {
1241        let mut sut = CyclicArray::<String>::new(10);
1242        for _ in 0..7 {
1243            let value = ulid::Ulid::new().to_string();
1244            sut.push_back(value);
1245        }
1246        sut.clear();
1247        for _ in 0..7 {
1248            let value = ulid::Ulid::new().to_string();
1249            sut.push_back(value);
1250        }
1251        sut.clear();
1252        for _ in 0..7 {
1253            let value = ulid::Ulid::new().to_string();
1254            sut.push_back(value);
1255        }
1256        sut.clear();
1257    }
1258
1259    #[test]
1260    fn test_cyclic_array_drop_partial() {
1261        let mut sut = CyclicArray::<String>::new(10);
1262        for _ in 0..7 {
1263            let value = ulid::Ulid::new().to_string();
1264            sut.push_back(value);
1265        }
1266        drop(sut);
1267    }
1268
1269    #[test]
1270    fn test_cyclic_array_drop_full() {
1271        let mut sut = CyclicArray::<String>::new(10);
1272        for _ in 0..sut.capacity() {
1273            let value = ulid::Ulid::new().to_string();
1274            sut.push_back(value);
1275        }
1276        drop(sut);
1277    }
1278
1279    #[test]
1280    fn test_cyclic_array_drop_wrapped() {
1281        let mut sut = CyclicArray::<String>::new(10);
1282        // push enough to almost fill the buffer
1283        for _ in 0..7 {
1284            let value = ulid::Ulid::new().to_string();
1285            sut.push_back(value);
1286        }
1287        // empty the buffer
1288        while !sut.is_empty() {
1289            sut.pop_front();
1290        }
1291        // push enough to wrap around to the start of the physical buffer
1292        for _ in 0..7 {
1293            let value = ulid::Ulid::new().to_string();
1294            sut.push_back(value);
1295        }
1296        drop(sut);
1297    }
1298
1299    #[test]
1300    #[should_panic(expected = "cyclic array is full")]
1301    fn test_cyclic_array_full_panic() {
1302        let mut sut = CyclicArray::<usize>::new(1);
1303        sut.push_back(10);
1304        sut.push_back(20);
1305    }
1306
1307    #[test]
1308    fn test_cyclic_array_wrapping() {
1309        let mut sut = CyclicArray::<usize>::new(10);
1310        // push enough to almost fill the buffer
1311        for value in 0..7 {
1312            sut.push_back(value);
1313        }
1314        // empty the buffer
1315        while !sut.is_empty() {
1316            sut.pop_front();
1317        }
1318        // push enough to wrap around to the start of the physical buffer
1319        for value in 0..7 {
1320            sut.push_back(value);
1321        }
1322
1323        assert_eq!(sut.get(1), Some(&1));
1324        assert_eq!(sut[1], 1);
1325        assert_eq!(sut.get(3), Some(&3));
1326        assert_eq!(sut[3], 3);
1327        assert_eq!(sut.get(6), Some(&6));
1328        assert_eq!(sut[6], 6);
1329        assert_eq!(sut.get(8), None);
1330
1331        // ensure values are removed correctly
1332        for value in 0..7 {
1333            assert_eq!(sut.pop_front(), Some(value));
1334        }
1335        assert_eq!(sut.len(), 0);
1336        assert_eq!(sut.capacity(), 10);
1337        assert!(sut.is_empty());
1338        assert!(!sut.is_full());
1339    }
1340
1341    #[test]
1342    fn test_cyclic_array_random_insert_remove() {
1343        let size = 128;
1344        let mut sut = CyclicArray::<usize>::new(size);
1345        for value in 1..=size {
1346            sut.push_back(value);
1347        }
1348        for _ in 0..1024 {
1349            let from = rand::random_range(0..size);
1350            let to = rand::random_range(0..size - 1);
1351            let value = sut.remove(from);
1352            sut.insert(to, value);
1353        }
1354        let mut sorted: Vec<usize> = vec![];
1355        while let Some(value) = sut.pop_front() {
1356            sorted.push(value);
1357        }
1358        sorted.sort();
1359        for (idx, value) in (1..=size).enumerate() {
1360            assert_eq!(sorted[idx], value);
1361        }
1362    }
1363
1364    #[test]
1365    fn test_cyclic_array_insert_head() {
1366        let mut sut = CyclicArray::<usize>::new(4);
1367        sut.insert(0, 4);
1368        sut.insert(0, 3);
1369        sut.insert(0, 2);
1370        sut.insert(0, 1);
1371        assert_eq!(sut.len(), 4);
1372        assert_eq!(sut[0], 1);
1373        assert_eq!(sut[1], 2);
1374        assert_eq!(sut[2], 3);
1375        assert_eq!(sut[3], 4);
1376    }
1377
1378    #[test]
1379    fn test_cyclic_array_insert_empty() {
1380        let mut sut = CyclicArray::<usize>::new(4);
1381        // start with:
1382        // ```
1383        // +---+---+---+---+
1384        // |   |   |   |   |
1385        // +---+---+---+---+
1386        // ```
1387        // becomes:
1388        // ```
1389        // +---+---+---+---+
1390        // | 1 |   |   |   |
1391        // +---+---+---+---+
1392        // ```
1393        sut.insert(0, 1);
1394        assert_eq!(sut[0], 1);
1395        assert_eq!(sut.len(), 1);
1396    }
1397
1398    #[test]
1399    fn test_cyclic_array_insert_empty_head_not_zero() {
1400        let mut sut = CyclicArray::<usize>::new(4);
1401        sut.push_back(1);
1402        sut.push_back(2);
1403        sut.pop_front();
1404        sut.pop_front();
1405        sut.insert(0, 1);
1406        assert_eq!(sut[0], 1);
1407        assert_eq!(sut.len(), 1);
1408    }
1409
1410    #[test]
1411    fn test_cyclic_array_insert_loop() {
1412        let mut sut = CyclicArray::<usize>::new(4);
1413        for value in 0..100 {
1414            sut.insert(0, value);
1415            sut.insert(0, value);
1416            sut.insert(0, value);
1417            sut.pop_front();
1418            sut.pop_front();
1419            sut.pop_front();
1420        }
1421        assert_eq!(sut.len(), 0);
1422        sut.push_back(1);
1423        sut.push_back(2);
1424        sut.push_back(3);
1425        sut.push_back(4);
1426        assert_eq!(sut.len(), 4);
1427        assert_eq!(sut[0], 1);
1428        assert_eq!(sut[1], 2);
1429        assert_eq!(sut[2], 3);
1430        assert_eq!(sut[3], 4);
1431    }
1432
1433    #[test]
1434    fn test_cyclic_array_insert_1() {
1435        let mut sut = CyclicArray::<usize>::new(4);
1436        // start with:
1437        // ```
1438        // +---+---+---+---+
1439        // | 1 | 2 |   |   |
1440        // +---+---+---+---+
1441        // ```
1442        // becomes:
1443        // ```
1444        // +---+---+---+---+
1445        // | 1 | 3 | 2 |   |
1446        // +---+---+---+---+
1447        // ```
1448        sut.push_back(1);
1449        sut.push_back(2);
1450        sut.insert(1, 3);
1451        assert_eq!(sut.len(), 3);
1452        assert_eq!(sut[0], 1);
1453        assert_eq!(sut[1], 3);
1454        assert_eq!(sut[2], 2);
1455    }
1456
1457    #[test]
1458    fn test_cyclic_array_insert_2() {
1459        let mut sut = CyclicArray::<usize>::new(4);
1460        // start with:
1461        // ```
1462        // +---+---+---+---+
1463        // | 2 |   |   | 1 |
1464        // +---+---+---+---+
1465        // ```
1466        // becomes:
1467        // ```
1468        // +---+---+---+---+
1469        // | 3 | 2 |   | 1 |
1470        // +---+---+---+---+
1471        // ```
1472        sut.push_back(1);
1473        sut.push_back(1);
1474        sut.push_back(1);
1475        sut.push_back(1);
1476        sut.pop_front();
1477        sut.pop_front();
1478        sut.pop_front();
1479        sut.push_back(2);
1480        sut.insert(1, 3);
1481        assert_eq!(sut.len(), 3);
1482        assert_eq!(sut[0], 1);
1483        assert_eq!(sut[1], 3);
1484        assert_eq!(sut[2], 2);
1485    }
1486
1487    #[test]
1488    fn test_cyclic_array_insert_3() {
1489        let mut sut = CyclicArray::<usize>::new(4);
1490        // start with:
1491        // ```
1492        // +---+---+---+---+
1493        // |   |   | 1 | 2 |
1494        // +---+---+---+---+
1495        // ```
1496        // becomes:
1497        // ```
1498        // +---+---+---+---+
1499        // |   | 1 | 3 | 2 |
1500        // +---+---+---+---+
1501        // ```
1502        sut.push_back(1);
1503        sut.push_back(1);
1504        sut.push_back(1);
1505        sut.push_back(2);
1506        sut.pop_front();
1507        sut.pop_front();
1508        sut.insert(1, 3);
1509        assert_eq!(sut.len(), 3);
1510        assert_eq!(sut[0], 1);
1511        assert_eq!(sut[1], 3);
1512        assert_eq!(sut[2], 2);
1513    }
1514
1515    #[test]
1516    fn test_cyclic_array_insert_4() {
1517        let mut sut = CyclicArray::<usize>::new(4);
1518        // start with:
1519        // ```
1520        // +---+---+---+---+
1521        // | 2 |   |   | 1 |
1522        // +---+---+---+---+
1523        // ```
1524        // becomes:
1525        // ```
1526        // +---+---+---+---+
1527        // | 2 |   | 3 | 1 |
1528        // +---+---+---+---+
1529        // ```
1530        sut.push_back(1);
1531        sut.push_back(1);
1532        sut.push_back(1);
1533        sut.push_back(1);
1534        sut.pop_front();
1535        sut.pop_front();
1536        sut.pop_front();
1537        sut.push_back(2);
1538        sut.insert(0, 3);
1539        assert_eq!(sut.len(), 3);
1540        assert_eq!(sut[0], 3);
1541        assert_eq!(sut[1], 1);
1542        assert_eq!(sut[2], 2);
1543    }
1544
1545    #[test]
1546    fn test_cyclic_array_insert_start() {
1547        let mut sut = CyclicArray::<usize>::new(4);
1548        // start with:
1549        // ```
1550        // +---+---+---+---+
1551        // | 1 | 2 |   |   |
1552        // +---+---+---+---+
1553        // ```
1554        // becomes:
1555        // ```
1556        // +---+---+---+---+
1557        // | 3 | 1 | 2 |   |
1558        // +---+---+---+---+
1559        // ```
1560        sut.push_back(1);
1561        sut.push_back(2);
1562        sut.insert(0, 3);
1563        assert_eq!(sut.len(), 3);
1564        assert_eq!(sut[0], 3);
1565        assert_eq!(sut[1], 1);
1566        assert_eq!(sut[2], 2);
1567    }
1568
1569    #[test]
1570    fn test_cyclic_array_insert_end() {
1571        let mut sut = CyclicArray::<usize>::new(4);
1572        // start with:
1573        // ```
1574        // +---+---+---+---+
1575        // | 1 | 2 |   |   |
1576        // +---+---+---+---+
1577        // ```
1578        // becomes:
1579        // ```
1580        // +---+---+---+---+
1581        // | 1 | 2 | 3 |   |
1582        // +---+---+---+---+
1583        // ```
1584        sut.push_back(1);
1585        sut.push_back(2);
1586        sut.insert(2, 3);
1587        assert_eq!(sut.len(), 3);
1588        assert_eq!(sut[0], 1);
1589        assert_eq!(sut[1], 2);
1590        assert_eq!(sut[2], 3);
1591    }
1592
1593    #[test]
1594    fn test_cyclic_array_insert_end_wrap() {
1595        let mut sut = CyclicArray::<usize>::new(4);
1596        // start with:
1597        // ```
1598        // +---+-V-+---+---+
1599        // |   | 2 | 3 | 4 |
1600        // +---+---+---+---+
1601        // ```
1602        // becomes:
1603        // ```
1604        // +---+-V-+---+---+
1605        // | 1 | 2 | 3 | 4 |
1606        // +---+---+---+---+
1607        // ```
1608        sut.push_back(1);
1609        sut.push_back(2);
1610        sut.push_back(3);
1611        sut.push_back(4);
1612        sut.pop_front();
1613        sut.insert(3, 1);
1614        assert_eq!(sut.len(), 4);
1615        assert_eq!(sut[0], 2);
1616        assert_eq!(sut[1], 3);
1617        assert_eq!(sut[2], 4);
1618        assert_eq!(sut[3], 1);
1619    }
1620
1621    #[test]
1622    #[should_panic(expected = "cyclic array is full")]
1623    fn test_cyclic_array_insert_full_panic() {
1624        let mut sut = CyclicArray::<usize>::new(1);
1625        sut.push_back(10);
1626        sut.insert(0, 20);
1627    }
1628
1629    #[test]
1630    #[should_panic(expected = "insertion index (is 2) should be <= len (is 0)")]
1631    fn test_cyclic_array_insert_bounds_panic() {
1632        let mut sut = CyclicArray::<usize>::new(1);
1633        sut.insert(2, 20);
1634    }
1635
1636    #[test]
1637    fn test_cyclic_array_remove_start() {
1638        let mut sut = CyclicArray::<usize>::new(4);
1639        // start with:
1640        // ```
1641        // +---+---+---+---+
1642        // | 1 | 2 | 3 |   |
1643        // +---+---+---+---+
1644        // ```
1645        // becomes:
1646        // ```
1647        // +---+---+---+---+
1648        // | 2 | 3 |   |   |
1649        // +---+---+---+---+
1650        // ```
1651        sut.push_back(1);
1652        sut.push_back(2);
1653        sut.push_back(3);
1654        sut.remove(0);
1655        assert_eq!(sut.len(), 2);
1656        assert_eq!(sut[0], 2);
1657        assert_eq!(sut[1], 3);
1658    }
1659
1660    #[test]
1661    fn test_cyclic_array_remove_1() {
1662        let mut sut = CyclicArray::<usize>::new(4);
1663        // start with:
1664        // ```
1665        // +---+---+---+---+
1666        // |   | 1 | 2 | 3 |
1667        // +---+---+---+---+
1668        // ```
1669        // becomes:
1670        // ```
1671        // +---+---+---+---+
1672        // |   |   | 1 | 3 |
1673        // +---+---+---+---+
1674        // ```
1675        sut.push_back(1);
1676        sut.push_back(1);
1677        sut.push_back(2);
1678        sut.push_back(3);
1679        sut.pop_front();
1680        sut.remove(1);
1681        assert_eq!(sut.len(), 2);
1682        assert_eq!(sut[0], 1);
1683        assert_eq!(sut[1], 3);
1684    }
1685
1686    #[test]
1687    fn test_cyclic_array_remove_2() {
1688        let mut sut = CyclicArray::<usize>::new(4);
1689        // start with:
1690        // ```
1691        // +---+---+---+---+
1692        // |   | 1 | 2 | 3 |
1693        // +---+---+---+---+
1694        // ```
1695        // becomes:
1696        // ```
1697        // +---+---+---+---+
1698        // |   |   | 2 | 3 |
1699        // +---+---+---+---+
1700        // ```
1701        sut.push_back(1);
1702        sut.push_back(1);
1703        sut.push_back(2);
1704        sut.push_back(3);
1705        sut.pop_front();
1706        sut.remove(0);
1707        assert_eq!(sut.len(), 2);
1708        assert_eq!(sut[0], 2);
1709        assert_eq!(sut[1], 3);
1710    }
1711
1712    #[test]
1713    fn test_cyclic_array_remove_3() {
1714        let mut sut = CyclicArray::<usize>::new(4);
1715        // start with:
1716        // ```
1717        // +---+---+---+---+
1718        // | 2 | 3 |   | 1 |
1719        // +---+---+---+---+
1720        // ```
1721        // becomes:
1722        // ```
1723        // +---+---+---+---+
1724        // | 3 |   |   | 1 |
1725        // +---+---+---+---+
1726        // ```
1727        sut.push_back(1);
1728        sut.push_back(1);
1729        sut.push_back(1);
1730        sut.push_back(1);
1731        sut.pop_front();
1732        sut.pop_front();
1733        sut.pop_front();
1734        sut.push_back(2);
1735        sut.push_back(3);
1736        sut.remove(1);
1737        assert_eq!(sut.len(), 2);
1738        assert_eq!(sut[0], 1);
1739        assert_eq!(sut[1], 3);
1740    }
1741
1742    #[test]
1743    fn test_cyclic_array_remove_start_full() {
1744        let mut sut = CyclicArray::<usize>::new(4);
1745        // start with:
1746        // ```
1747        // +---+---+---+---+
1748        // | 1 | 2 | 3 | 4 |
1749        // +---+---+---+---+
1750        // ```
1751        // becomes:
1752        // ```
1753        // +---+---+---+---+
1754        // | 2 | 3 | 4 |   |
1755        // +---+---+---+---+
1756        // ```
1757        sut.push_back(1);
1758        sut.push_back(2);
1759        sut.push_back(3);
1760        sut.push_back(4);
1761        sut.remove(0);
1762        assert_eq!(sut.len(), 3);
1763        assert_eq!(sut[0], 2);
1764        assert_eq!(sut[1], 3);
1765        assert_eq!(sut[2], 4);
1766    }
1767
1768    #[test]
1769    fn test_cyclic_array_remove_middle_full() {
1770        let mut sut = CyclicArray::<usize>::new(4);
1771        // start with:
1772        // ```
1773        // +---+---+---+---+
1774        // | 1 | 2 | 3 | 4 |
1775        // +---+---+---+---+
1776        // ```
1777        // becomes:
1778        // ```
1779        // +---+---+---+---+
1780        // | 1 | 2 | 4 |   |
1781        // +---+---+---+---+
1782        // ```
1783        sut.push_back(1);
1784        sut.push_back(2);
1785        sut.push_back(3);
1786        sut.push_back(4);
1787        sut.remove(2);
1788        assert_eq!(sut.len(), 3);
1789        assert_eq!(sut[0], 1);
1790        assert_eq!(sut[1], 2);
1791        assert_eq!(sut[2], 4);
1792    }
1793
1794    #[test]
1795    fn test_cyclic_array_remove_end() {
1796        let mut sut = CyclicArray::<usize>::new(4);
1797        // start with:
1798        // ```
1799        // +---+---+---+---+
1800        // | 1 | 2 | 3 |   |
1801        // +---+---+---+---+
1802        // ```
1803        // becomes:
1804        // ```
1805        // +---+---+---+---+
1806        // | 1 | 2 |   |   |
1807        // +---+---+---+---+
1808        // ```
1809        sut.push_back(1);
1810        sut.push_back(2);
1811        sut.push_back(3);
1812        sut.remove(2);
1813        assert_eq!(sut.len(), 2);
1814        assert_eq!(sut[0], 1);
1815        assert_eq!(sut[1], 2);
1816    }
1817
1818    #[test]
1819    fn test_cyclic_array_remove_end_full() {
1820        let mut sut = CyclicArray::<usize>::new(4);
1821        // start with:
1822        // ```
1823        // +---+---+---+---+
1824        // | 1 | 2 | 3 | 4 |
1825        // +---+---+---+---+
1826        // ```
1827        // becomes:
1828        // ```
1829        // +---+---+---+---+
1830        // | 1 | 2 | 3 |   |
1831        // +---+---+---+---+
1832        // ```
1833        sut.push_back(1);
1834        sut.push_back(2);
1835        sut.push_back(3);
1836        sut.push_back(4);
1837        sut.remove(3);
1838        assert_eq!(sut.len(), 3);
1839        assert_eq!(sut[0], 1);
1840        assert_eq!(sut[1], 2);
1841        assert_eq!(sut[2], 3);
1842    }
1843
1844    #[test]
1845    fn test_cyclic_array_remove_end_wrap() {
1846        let mut sut = CyclicArray::<usize>::new(4);
1847        // start with:
1848        // ```
1849        // +---+-V-+---+---+
1850        // | 5 | 2 | 3 | 4 |
1851        // +---+---+---+---+
1852        // ```
1853        // becomes:
1854        // ```
1855        // +---+-V-+---+---+
1856        // |   | 2 | 3 | 4 |
1857        // +---+---+---+---+
1858        // ```
1859        sut.push_back(1);
1860        sut.push_back(2);
1861        sut.push_back(3);
1862        sut.push_back(4);
1863        sut.pop_front();
1864        sut.push_back(5);
1865        assert_eq!(sut.len(), 4);
1866        assert_eq!(sut[0], 2);
1867        assert_eq!(sut[1], 3);
1868        assert_eq!(sut[2], 4);
1869        assert_eq!(sut[3], 5);
1870        sut.remove(3);
1871        assert_eq!(sut.len(), 3);
1872        assert_eq!(sut[0], 2);
1873        assert_eq!(sut[1], 3);
1874        assert_eq!(sut[2], 4);
1875    }
1876
1877    #[test]
1878    fn test_cyclic_array_push_pop_remove() {
1879        let mut sut = CyclicArray::<usize>::new(4);
1880        sut.push_back(7);
1881        sut.push_back(7);
1882        sut.push_back(7);
1883        sut.push_back(8);
1884        sut.pop_front();
1885        sut.pop_front();
1886        sut.push_back(10);
1887        sut.push_back(11);
1888        sut.remove(2);
1889        assert_eq!(sut.len(), 3);
1890        assert_eq!(sut[0], 7);
1891        assert_eq!(sut[1], 8);
1892        assert_eq!(sut[2], 11);
1893    }
1894
1895    #[test]
1896    fn test_cyclic_array_push_pop_insert() {
1897        let mut sut = CyclicArray::<usize>::new(4);
1898        sut.push_back(11);
1899        sut.push_back(11);
1900        sut.push_back(11);
1901        sut.push_back(12);
1902        sut.pop_front();
1903        sut.pop_front();
1904        sut.push_back(4);
1905        sut.insert(2, 3);
1906        assert_eq!(sut.len(), 4);
1907        assert_eq!(sut[0], 11);
1908        assert_eq!(sut[1], 12);
1909        assert_eq!(sut[2], 3);
1910        assert_eq!(sut[3], 4);
1911    }
1912
1913    #[test]
1914    #[should_panic(expected = "removal index (is 2) should be < len (is 0)")]
1915    fn test_cyclic_array_remove_bounds_panic() {
1916        let mut sut = CyclicArray::<usize>::new(1);
1917        sut.remove(2);
1918    }
1919
1920    #[test]
1921    fn test_cyclic_array_from_string() {
1922        let mut sut = CyclicArray::<String>::new(4);
1923        sut.push_back(ulid::Ulid::new().to_string());
1924        sut.push_back(ulid::Ulid::new().to_string());
1925        sut.push_back(ulid::Ulid::new().to_string());
1926        let copy = CyclicArray::<String>::from(8, sut);
1927        assert_eq!(copy.len(), 3);
1928        assert_eq!(copy.capacity(), 8);
1929        assert!(!copy[0].is_empty());
1930        assert!(!copy[1].is_empty());
1931        assert!(!copy[2].is_empty());
1932    }
1933
1934    #[test]
1935    fn test_cyclic_array_from_smaller_1() {
1936        let mut sut = CyclicArray::<usize>::new(4);
1937        sut.push_back(1);
1938        sut.push_back(2);
1939        sut.push_back(3);
1940        let copy = CyclicArray::<usize>::from(8, sut);
1941        assert_eq!(copy.len(), 3);
1942        assert_eq!(copy.capacity(), 8);
1943        assert_eq!(copy[0], 1);
1944        assert_eq!(copy[1], 2);
1945        assert_eq!(copy[2], 3);
1946    }
1947
1948    #[test]
1949    fn test_cyclic_array_from_smaller_2() {
1950        let mut sut = CyclicArray::<usize>::new(4);
1951        sut.push_back(1);
1952        sut.push_back(1);
1953        sut.push_back(1);
1954        sut.push_back(2);
1955        sut.pop_front();
1956        sut.pop_front();
1957        sut.push_back(3);
1958        sut.push_back(4);
1959        let copy = CyclicArray::<usize>::from(8, sut);
1960        assert_eq!(copy.len(), 4);
1961        assert_eq!(copy.capacity(), 8);
1962        assert_eq!(copy[0], 1);
1963        assert_eq!(copy[1], 2);
1964        assert_eq!(copy[2], 3);
1965        assert_eq!(copy[3], 4);
1966    }
1967
1968    #[test]
1969    fn test_cyclic_array_from_larger_1() {
1970        let mut sut = CyclicArray::<usize>::new(8);
1971        sut.push_back(1);
1972        sut.push_back(2);
1973        sut.push_back(3);
1974        let copy = CyclicArray::<usize>::from(4, sut);
1975        assert_eq!(copy.len(), 3);
1976        assert_eq!(copy.capacity(), 4);
1977        assert_eq!(copy[0], 1);
1978        assert_eq!(copy[1], 2);
1979        assert_eq!(copy[2], 3);
1980    }
1981
1982    #[test]
1983    fn test_cyclic_array_from_larger_2() {
1984        let mut sut = CyclicArray::<usize>::new(8);
1985        for _ in 0..7 {
1986            sut.push_back(1);
1987        }
1988        sut.push_back(2);
1989        for _ in 0..6 {
1990            sut.pop_front();
1991        }
1992        sut.push_back(3);
1993        let copy = CyclicArray::<usize>::from(4, sut);
1994        assert_eq!(copy.len(), 3);
1995        assert_eq!(copy.capacity(), 4);
1996        assert_eq!(copy[0], 1);
1997        assert_eq!(copy[1], 2);
1998        assert_eq!(copy[2], 3);
1999    }
2000
2001    #[test]
2002    fn test_cyclic_array_combine_string() {
2003        let mut a = CyclicArray::<String>::new(4);
2004        a.push_back(ulid::Ulid::new().to_string());
2005        a.push_back(ulid::Ulid::new().to_string());
2006        a.push_back(ulid::Ulid::new().to_string());
2007        let mut b = CyclicArray::<String>::new(4);
2008        b.push_back(ulid::Ulid::new().to_string());
2009        b.push_back(ulid::Ulid::new().to_string());
2010        b.push_back(ulid::Ulid::new().to_string());
2011        let sut = CyclicArray::combine(a, b);
2012        assert_eq!(sut.len(), 6);
2013        assert_eq!(sut.capacity(), 8);
2014        for i in 0..6 {
2015            assert!(!sut[i].is_empty());
2016        }
2017    }
2018
2019    #[test]
2020    fn test_cyclic_array_combine_1_1() {
2021        let mut a = CyclicArray::<usize>::new(4);
2022        a.push_back(1);
2023        a.push_back(2);
2024        a.push_back(3);
2025        let mut b = CyclicArray::<usize>::new(4);
2026        b.push_back(4);
2027        b.push_back(5);
2028        b.push_back(6);
2029        let sut = CyclicArray::combine(a, b);
2030        assert_eq!(sut.len(), 6);
2031        assert_eq!(sut.capacity(), 8);
2032        for i in 0..6 {
2033            assert_eq!(sut[i], i + 1);
2034        }
2035    }
2036
2037    #[test]
2038    fn test_cyclic_array_combine_1_2() {
2039        let mut a = CyclicArray::<usize>::new(4);
2040        a.push_back(1);
2041        a.push_back(2);
2042        a.push_back(3);
2043        let mut b = CyclicArray::<usize>::new(4);
2044        b.push_back(4);
2045        b.push_back(4);
2046        b.push_back(4);
2047        b.push_back(5);
2048        b.pop_front();
2049        b.pop_front();
2050        b.push_back(6);
2051        let sut = CyclicArray::combine(a, b);
2052        assert_eq!(sut.len(), 6);
2053        assert_eq!(sut.capacity(), 8);
2054        for i in 0..6 {
2055            assert_eq!(sut[i], i + 1);
2056        }
2057    }
2058
2059    #[test]
2060    fn test_cyclic_array_combine_2_1() {
2061        let mut a = CyclicArray::<usize>::new(4);
2062        a.push_back(1);
2063        a.push_back(1);
2064        a.push_back(1);
2065        a.push_back(2);
2066        a.pop_front();
2067        a.pop_front();
2068        a.push_back(3);
2069        let mut b = CyclicArray::<usize>::new(4);
2070        b.push_back(4);
2071        b.push_back(5);
2072        b.push_back(6);
2073        let sut = CyclicArray::combine(a, b);
2074        assert_eq!(sut.len(), 6);
2075        assert_eq!(sut.capacity(), 8);
2076        for i in 0..6 {
2077            assert_eq!(sut[i], i + 1);
2078        }
2079    }
2080
2081    #[test]
2082    fn test_cyclic_array_combine_2_2() {
2083        let mut a = CyclicArray::<usize>::new(4);
2084        a.push_back(1);
2085        a.push_back(1);
2086        a.push_back(1);
2087        a.push_back(2);
2088        a.pop_front();
2089        a.pop_front();
2090        a.push_back(3);
2091        let mut b = CyclicArray::<usize>::new(4);
2092        b.push_back(4);
2093        b.push_back(4);
2094        b.push_back(4);
2095        b.push_back(5);
2096        b.pop_front();
2097        b.pop_front();
2098        b.push_back(6);
2099        let sut = CyclicArray::combine(a, b);
2100        assert_eq!(sut.len(), 6);
2101        assert_eq!(sut.capacity(), 8);
2102        for i in 0..6 {
2103            assert_eq!(sut[i], i + 1);
2104        }
2105    }
2106
2107    #[test]
2108    fn test_cyclic_array_split_empty() {
2109        let big = CyclicArray::<usize>::new(8);
2110        let (a, b) = big.split();
2111        assert_eq!(a.len(), 0);
2112        assert_eq!(a.capacity(), 4);
2113        assert_eq!(b.len(), 0);
2114        assert_eq!(b.capacity(), 4);
2115    }
2116
2117    #[test]
2118    fn test_cyclic_array_split_string() {
2119        let mut big = CyclicArray::<String>::new(8);
2120        for _ in 0..8 {
2121            big.push_back(ulid::Ulid::new().to_string());
2122        }
2123        let (a, b) = big.split();
2124        assert_eq!(a.len(), 4);
2125        assert_eq!(a.capacity(), 4);
2126        assert!(!a[0].is_empty());
2127        assert!(!a[1].is_empty());
2128        assert!(!a[2].is_empty());
2129        assert!(!a[3].is_empty());
2130        assert_eq!(b.len(), 4);
2131        assert_eq!(b.capacity(), 4);
2132        assert!(!b[0].is_empty());
2133        assert!(!b[1].is_empty());
2134        assert!(!b[2].is_empty());
2135        assert!(!b[3].is_empty());
2136    }
2137
2138    #[test]
2139    fn test_cyclic_array_split_full() {
2140        let mut big = CyclicArray::<usize>::new(8);
2141        for value in 1..=8 {
2142            big.push_back(value);
2143        }
2144        let (a, b) = big.split();
2145        assert_eq!(a.len(), 4);
2146        assert_eq!(a.capacity(), 4);
2147        assert_eq!(a[0], 1);
2148        assert_eq!(a[1], 2);
2149        assert_eq!(a[2], 3);
2150        assert_eq!(a[3], 4);
2151        assert_eq!(b.len(), 4);
2152        assert_eq!(b.capacity(), 4);
2153        assert_eq!(b[0], 5);
2154        assert_eq!(b[1], 6);
2155        assert_eq!(b[2], 7);
2156        assert_eq!(b[3], 8);
2157    }
2158
2159    #[test]
2160    fn test_cyclic_array_split_partial_whole() {
2161        let mut big = CyclicArray::<usize>::new(8);
2162        for value in 1..=6 {
2163            big.push_back(value);
2164        }
2165        let (a, b) = big.split();
2166        assert_eq!(a.len(), 4);
2167        assert_eq!(a.capacity(), 4);
2168        assert_eq!(a[0], 1);
2169        assert_eq!(a[1], 2);
2170        assert_eq!(a[2], 3);
2171        assert_eq!(a[3], 4);
2172        assert_eq!(b.len(), 2);
2173        assert_eq!(b.capacity(), 4);
2174        assert_eq!(b[0], 5);
2175        assert_eq!(b[1], 6);
2176    }
2177
2178    #[test]
2179    fn test_cyclic_array_split_partial_split() {
2180        let mut big = CyclicArray::<usize>::new(8);
2181        for value in 1..=6 {
2182            big.push_back(value);
2183        }
2184        big.pop_front();
2185        big.pop_front();
2186        big.pop_front();
2187        big.push_back(7);
2188        big.push_back(8);
2189        big.push_back(9);
2190        let (a, b) = big.split();
2191        assert_eq!(a.len(), 4);
2192        assert_eq!(a.capacity(), 4);
2193        assert_eq!(a[0], 4);
2194        assert_eq!(a[1], 5);
2195        assert_eq!(a[2], 6);
2196        assert_eq!(a[3], 7);
2197        assert_eq!(b.len(), 2);
2198        assert_eq!(b.capacity(), 4);
2199        assert_eq!(b[0], 8);
2200        assert_eq!(b[1], 9);
2201    }
2202
2203    #[test]
2204    fn test_cyclic_array_get_mut() {
2205        let mut sut = CyclicArray::<usize>::new(4);
2206        sut.push_back(1);
2207        sut.push_back(2);
2208        sut.push_back(3);
2209        sut.push_back(4);
2210        if let Some(value) = sut.get_mut(1) {
2211            *value = 12;
2212        } else {
2213            panic!("get_mut() returned None")
2214        }
2215        sut[2] = 13;
2216        assert_eq!(sut[0], 1);
2217        assert_eq!(sut[1], 12);
2218        assert_eq!(sut[2], 13);
2219        assert_eq!(sut[3], 4);
2220    }
2221}