Skip to main content

certeza/vec/
mod.rs

1#![allow(unsafe_code)]
2//! # `TruenoVec` - A Growable Array Type with Verified Correctness
3//!
4//! This module provides `TruenoVec<T>`, a custom growable vector implementation
5//! that demonstrates the certeza framework's tiered testing approach:
6//!
7//! - **Tier 1**: Unit tests for basic functionality (sub-second feedback)
8//! - **Tier 2**: Property-based tests verifying algebraic properties (1-5 minutes)
9//! - **Tier 3**: Formal verification of critical invariants with Kani (hours)
10//!
11//! ## Safety Invariants
12//!
13//! The following invariants are maintained and formally verified:
14//!
15//! 1. `ptr` is either null or points to valid memory for `capacity` elements
16//! 2. `len <= capacity` at all times
17//! 3. Elements `[0..len)` are initialized
18//! 4. Elements `[len..capacity)` are uninitialized
19//!
20//! ## Risk Classification
21//!
22//! **Very High Risk** - Contains `unsafe` code for manual memory management.
23//! Full verification framework applied:
24//! - Property-based testing
25//! - 95%+ coverage requirement
26//! - >85% mutation score target
27//! - Formal verification of invariants
28//!
29//! ## Example
30//!
31//! ```rust
32//! use certeza::TruenoVec;
33//!
34//! let mut vec = TruenoVec::new();
35//! vec.push(1);
36//! vec.push(2);
37//! vec.push(3);
38//!
39//! assert_eq!(vec.len(), 3);
40//! assert_eq!(vec.get(1), Some(&2));
41//! assert_eq!(vec.pop(), Some(3));
42//! ```
43
44use std::alloc::{self, Layout};
45use std::marker::PhantomData;
46use std::ptr::{self, NonNull};
47
48/// A growable array type with verified correctness properties.
49///
50/// This implementation demonstrates asymptotic test effectiveness through:
51/// - 95%+ line coverage
52/// - >85% mutation score
53/// - Comprehensive property-based test suite
54/// - Formal verification of critical invariants
55///
56/// # Type Parameters
57///
58/// * `T` - The type of elements stored in the vector
59///
60/// # Safety
61///
62/// This type uses `unsafe` code for manual memory management. All safety
63/// invariants are formally verified using Kani and tested using property-based
64/// testing with proptest.
65///
66/// # Examples
67///
68/// ```rust
69/// use certeza::TruenoVec;
70///
71/// let mut v = TruenoVec::new();
72/// v.push(1);
73/// v.push(2);
74/// assert_eq!(v.len(), 2);
75/// assert_eq!(v.pop(), Some(2));
76/// ```
77pub struct TruenoVec<T> {
78    ptr: NonNull<T>,
79    len: usize,
80    capacity: usize,
81    _marker: PhantomData<T>,
82}
83
84// ============================================================================
85// Core Implementation
86// ============================================================================
87
88impl<T> TruenoVec<T> {
89    /// Creates a new, empty `TruenoVec<T>`.
90    ///
91    /// The vector will not allocate until elements are pushed onto it.
92    ///
93    /// # Complexity
94    ///
95    /// - Time: O(1)
96    /// - Space: O(1)
97    ///
98    /// # Examples
99    ///
100    /// ```rust
101    /// use certeza::TruenoVec;
102    ///
103    /// let mut vec: TruenoVec<i32> = TruenoVec::new();
104    /// assert_eq!(vec.len(), 0);
105    /// assert_eq!(vec.capacity(), 0);
106    /// ```
107    #[must_use]
108    pub const fn new() -> Self {
109        Self { ptr: NonNull::dangling(), len: 0, capacity: 0, _marker: PhantomData }
110    }
111
112    /// Creates a new, empty `TruenoVec<T>` with the specified capacity.
113    ///
114    /// The vector will be able to hold exactly `capacity` elements without
115    /// reallocating. If `capacity` is 0, the vector will not allocate.
116    ///
117    /// # Complexity
118    ///
119    /// - Time: O(n) where n is the capacity
120    /// - Space: O(n)
121    ///
122    /// # Panics
123    ///
124    /// Panics if the capacity exceeds `isize::MAX` bytes or if allocation fails.
125    ///
126    /// # Examples
127    ///
128    /// ```rust
129    /// use certeza::TruenoVec;
130    ///
131    /// let mut vec: TruenoVec<i32> = TruenoVec::with_capacity(10);
132    /// assert_eq!(vec.len(), 0);
133    /// assert_eq!(vec.capacity(), 10);
134    ///
135    /// // These pushes won't reallocate
136    /// for i in 0..10 {
137    ///     vec.push(i);
138    /// }
139    /// assert_eq!(vec.capacity(), 10);
140    /// ```
141    #[must_use]
142    pub fn with_capacity(capacity: usize) -> Self {
143        if capacity == 0 {
144            Self::new()
145        } else {
146            let layout = Layout::array::<T>(capacity).expect("capacity overflow");
147            // SAFETY: layout has non-zero size
148            let ptr = unsafe {
149                let ptr = alloc::alloc(layout).cast::<T>();
150                NonNull::new(ptr).expect("allocation failed")
151            };
152            Self { ptr, len: 0, capacity, _marker: PhantomData }
153        }
154    }
155
156    /// Returns the number of elements in the vector.
157    ///
158    /// # Complexity
159    ///
160    /// O(1)
161    ///
162    /// # Examples
163    ///
164    /// ```rust
165    /// use certeza::TruenoVec;
166    ///
167    /// let mut vec = TruenoVec::new();
168    /// assert_eq!(vec.len(), 0);
169    /// vec.push(1);
170    /// assert_eq!(vec.len(), 1);
171    /// ```
172    #[must_use]
173    pub const fn len(&self) -> usize {
174        self.len
175    }
176
177    /// Returns `true` if the vector contains no elements.
178    ///
179    /// # Complexity
180    ///
181    /// O(1)
182    ///
183    /// # Examples
184    ///
185    /// ```rust
186    /// use certeza::TruenoVec;
187    ///
188    /// let mut vec = TruenoVec::new();
189    /// assert!(vec.is_empty());
190    /// vec.push(1);
191    /// assert!(!vec.is_empty());
192    /// ```
193    #[must_use]
194    pub const fn is_empty(&self) -> bool {
195        self.len == 0
196    }
197
198    /// Returns the number of elements the vector can hold without reallocating.
199    ///
200    /// # Complexity
201    ///
202    /// O(1)
203    ///
204    /// # Examples
205    ///
206    /// ```rust
207    /// use certeza::TruenoVec;
208    ///
209    /// let vec: TruenoVec<i32> = TruenoVec::with_capacity(10);
210    /// assert_eq!(vec.capacity(), 10);
211    /// ```
212    #[must_use]
213    pub const fn capacity(&self) -> usize {
214        self.capacity
215    }
216
217    /// Appends an element to the back of the vector.
218    ///
219    /// # Complexity
220    ///
221    /// - Amortized O(1) time
222    /// - Worst-case O(n) when reallocation is needed
223    ///
224    /// # Panics
225    ///
226    /// Panics if the new capacity exceeds `isize::MAX` bytes.
227    ///
228    /// # Examples
229    ///
230    /// ```rust
231    /// use certeza::TruenoVec;
232    ///
233    /// let mut vec = TruenoVec::new();
234    /// vec.push(1);
235    /// vec.push(2);
236    /// assert_eq!(vec.len(), 2);
237    /// assert_eq!(vec.get(0), Some(&1));
238    /// assert_eq!(vec.get(1), Some(&2));
239    /// ```
240    pub fn push(&mut self, value: T) {
241        if self.len == self.capacity {
242            self.grow();
243        }
244        // SAFETY: len < capacity after grow, ptr is valid
245        unsafe {
246            ptr::write(self.ptr.as_ptr().add(self.len), value);
247        }
248        self.len += 1;
249    }
250
251    /// Removes the last element from the vector and returns it, or `None` if empty.
252    ///
253    /// # Complexity
254    ///
255    /// O(1)
256    ///
257    /// # Examples
258    ///
259    /// ```rust
260    /// use certeza::TruenoVec;
261    ///
262    /// let mut vec = TruenoVec::new();
263    /// vec.push(1);
264    /// vec.push(2);
265    /// assert_eq!(vec.pop(), Some(2));
266    /// assert_eq!(vec.pop(), Some(1));
267    /// assert_eq!(vec.pop(), None);
268    /// ```
269    #[allow(clippy::missing_const_for_fn)] // Cannot be const due to ptr::read
270    pub fn pop(&mut self) -> Option<T> {
271        if self.len == 0 {
272            None
273        } else {
274            self.len -= 1;
275            // SAFETY: len was > 0, so len-1 is a valid initialized index
276            unsafe { Some(ptr::read(self.ptr.as_ptr().add(self.len))) }
277        }
278    }
279
280    /// Returns a reference to an element at the given index, or `None` if out of bounds.
281    ///
282    /// # Complexity
283    ///
284    /// O(1)
285    ///
286    /// # Examples
287    ///
288    /// ```rust
289    /// use certeza::TruenoVec;
290    ///
291    /// let mut vec = TruenoVec::new();
292    /// vec.push(10);
293    /// vec.push(20);
294    /// vec.push(30);
295    /// assert_eq!(vec.get(1), Some(&20));
296    /// assert_eq!(vec.get(3), None);
297    /// ```
298    #[must_use]
299    pub fn get(&self, index: usize) -> Option<&T> {
300        if index < self.len {
301            // SAFETY: index < len, so it's a valid initialized element
302            unsafe { Some(&*self.ptr.as_ptr().add(index)) }
303        } else {
304            None
305        }
306    }
307
308    /// Returns a mutable reference to an element at the given index, or `None` if out of bounds.
309    ///
310    /// # Complexity
311    ///
312    /// O(1)
313    ///
314    /// # Examples
315    ///
316    /// ```rust
317    /// use certeza::TruenoVec;
318    ///
319    /// let mut vec = TruenoVec::new();
320    /// vec.push(10);
321    /// vec.push(20);
322    /// if let Some(elem) = vec.get_mut(1) {
323    ///     *elem = 25;
324    /// }
325    /// assert_eq!(vec.get(1), Some(&25));
326    /// ```
327    #[must_use]
328    pub fn get_mut(&mut self, index: usize) -> Option<&mut T> {
329        if index < self.len {
330            // SAFETY: index < len, so it's a valid initialized element
331            unsafe { Some(&mut *self.ptr.as_ptr().add(index)) }
332        } else {
333            None
334        }
335    }
336
337    /// Clears the vector, removing all values.
338    ///
339    /// This method removes all elements from the vector but does not change
340    /// its capacity. The allocated memory is retained for reuse.
341    ///
342    /// # Complexity
343    ///
344    /// O(n) where n is the number of elements
345    ///
346    /// # Examples
347    ///
348    /// ```rust
349    /// use certeza::TruenoVec;
350    ///
351    /// let mut vec = TruenoVec::new();
352    /// vec.push(1);
353    /// vec.push(2);
354    /// vec.push(3);
355    ///
356    /// let capacity = vec.capacity();
357    /// vec.clear();
358    ///
359    /// assert_eq!(vec.len(), 0);
360    /// assert_eq!(vec.capacity(), capacity); // Capacity unchanged
361    /// assert!(vec.is_empty());
362    /// ```
363    pub fn clear(&mut self) {
364        while self.pop().is_some() {}
365    }
366
367    /// Inserts an element at position `index`, shifting all elements after it
368    /// to the right.
369    ///
370    /// # Complexity
371    ///
372    /// - Time: O(n) where n is the number of elements after the insertion point
373    /// - Space: O(1) amortized (may reallocate if capacity is exceeded)
374    ///
375    /// # Panics
376    ///
377    /// Panics if `index > len()`.
378    ///
379    /// # Examples
380    ///
381    /// ```rust
382    /// use certeza::TruenoVec;
383    ///
384    /// let mut vec = TruenoVec::new();
385    /// vec.push(1);
386    /// vec.push(3);
387    /// vec.insert(1, 2); // Insert 2 at index 1
388    ///
389    /// assert_eq!(vec.get(0), Some(&1));
390    /// assert_eq!(vec.get(1), Some(&2));
391    /// assert_eq!(vec.get(2), Some(&3));
392    /// ```
393    pub fn insert(&mut self, index: usize, value: T) {
394        assert!(index <= self.len, "insertion index out of bounds");
395
396        if self.len == self.capacity {
397            self.grow();
398        }
399
400        // SAFETY: len < capacity after grow, index <= len
401        unsafe {
402            let ptr = self.ptr.as_ptr();
403            // Shift elements [index..len) one position to the right
404            if index < self.len {
405                ptr::copy(ptr.add(index), ptr.add(index + 1), self.len - index);
406            }
407            // Write the new value at index
408            ptr::write(ptr.add(index), value);
409        }
410
411        self.len += 1;
412    }
413
414    /// Removes and returns the element at position `index`, shifting all
415    /// elements after it to the left.
416    ///
417    /// # Complexity
418    ///
419    /// O(n) where n is the number of elements after the removal point
420    ///
421    /// # Panics
422    ///
423    /// Panics if `index >= len()`.
424    ///
425    /// # Examples
426    ///
427    /// ```rust
428    /// use certeza::TruenoVec;
429    ///
430    /// let mut vec = TruenoVec::new();
431    /// vec.push(1);
432    /// vec.push(2);
433    /// vec.push(3);
434    ///
435    /// let removed = vec.remove(1);
436    /// assert_eq!(removed, 2);
437    /// assert_eq!(vec.len(), 2);
438    /// assert_eq!(vec.get(0), Some(&1));
439    /// assert_eq!(vec.get(1), Some(&3));
440    /// ```
441    pub fn remove(&mut self, index: usize) -> T {
442        assert!(index < self.len, "removal index out of bounds");
443
444        // SAFETY: index < len, so it's a valid initialized element
445        unsafe {
446            let ptr = self.ptr.as_ptr();
447            // Read the value at index
448            let value = ptr::read(ptr.add(index));
449            // Shift elements [index+1..len) one position to the left
450            if index < self.len - 1 {
451                ptr::copy(ptr.add(index + 1), ptr.add(index), self.len - index - 1);
452            }
453            self.len -= 1;
454            value
455        }
456    }
457
458    /// Returns an immutable slice containing all elements of the vector.
459    ///
460    /// This provides a safe view into the vector's contents without copying.
461    ///
462    /// # Complexity
463    ///
464    /// O(1)
465    ///
466    /// # Examples
467    ///
468    /// ```rust
469    /// use certeza::TruenoVec;
470    ///
471    /// let mut vec = TruenoVec::new();
472    /// vec.push(1);
473    /// vec.push(2);
474    /// vec.push(3);
475    ///
476    /// let slice = vec.as_slice();
477    /// assert_eq!(slice, &[1, 2, 3]);
478    /// assert_eq!(slice.len(), 3);
479    /// ```
480    #[must_use]
481    pub const fn as_slice(&self) -> &[T] {
482        // SAFETY: ptr points to len initialized elements
483        unsafe { std::slice::from_raw_parts(self.ptr.as_ptr(), self.len) }
484    }
485
486    /// Returns a mutable slice containing all elements of the vector.
487    ///
488    /// This provides a safe mutable view into the vector's contents without copying.
489    ///
490    /// # Complexity
491    ///
492    /// O(1)
493    ///
494    /// # Examples
495    ///
496    /// ```rust
497    /// use certeza::TruenoVec;
498    ///
499    /// let mut vec = TruenoVec::new();
500    /// vec.push(1);
501    /// vec.push(2);
502    /// vec.push(3);
503    ///
504    /// let slice = vec.as_slice_mut();
505    /// slice[1] = 10;
506    /// assert_eq!(vec.get(1), Some(&10));
507    /// ```
508    #[must_use]
509    pub const fn as_slice_mut(&mut self) -> &mut [T] {
510        // SAFETY: ptr points to len initialized elements
511        unsafe { std::slice::from_raw_parts_mut(self.ptr.as_ptr(), self.len) }
512    }
513
514    /// Doubles the capacity of the vector.
515    ///
516    /// Uses a growth factor of 2x for exponential growth, ensuring amortized O(1) push.
517    ///
518    /// # Panics
519    ///
520    /// Panics if the new capacity exceeds `isize::MAX` bytes.
521    fn grow(&mut self) {
522        let new_capacity = if self.capacity == 0 {
523            1
524        } else {
525            self.capacity.checked_mul(2).expect("capacity overflow")
526        };
527
528        let new_layout = Layout::array::<T>(new_capacity).expect("capacity overflow");
529
530        let new_ptr = if self.capacity == 0 {
531            // SAFETY: new_layout has non-zero size
532            unsafe {
533                let ptr = alloc::alloc(new_layout).cast::<T>();
534                NonNull::new(ptr).expect("allocation failed")
535            }
536        } else {
537            let old_layout = Layout::array::<T>(self.capacity).expect("capacity overflow");
538            // SAFETY: ptr is valid, old_layout matches the current allocation
539            unsafe {
540                let ptr =
541                    alloc::realloc(self.ptr.as_ptr().cast::<u8>(), old_layout, new_layout.size())
542                        .cast::<T>();
543                NonNull::new(ptr).expect("allocation failed")
544            }
545        };
546
547        self.ptr = new_ptr;
548        self.capacity = new_capacity;
549    }
550}
551
552// ============================================================================
553// Trait Implementations
554// ============================================================================
555
556impl<T> Default for TruenoVec<T> {
557    fn default() -> Self {
558        Self::new()
559    }
560}
561
562impl<T> Drop for TruenoVec<T> {
563    fn drop(&mut self) {
564        // Drop all elements
565        while self.pop().is_some() {}
566
567        // Deallocate memory if capacity > 0
568        if self.capacity > 0 {
569            let layout = Layout::array::<T>(self.capacity).expect("capacity overflow");
570            // SAFETY: ptr was allocated with this layout, all elements dropped
571            unsafe {
572                alloc::dealloc(self.ptr.as_ptr().cast::<u8>(), layout);
573            }
574        }
575    }
576}
577
578// Thread safety: TruenoVec<T> is Send if T is Send
579unsafe impl<T: Send> Send for TruenoVec<T> {}
580
581// Thread safety: TruenoVec<T> is Sync if T is Sync
582unsafe impl<T: Sync> Sync for TruenoVec<T> {}
583
584// ============================================================================
585// Conversion Trait Implementations
586// ============================================================================
587
588impl<T> From<Vec<T>> for TruenoVec<T> {
589    /// Converts a `Vec<T>` into a `TruenoVec<T>`.
590    ///
591    /// This conversion takes ownership of the `Vec` and efficiently reuses
592    /// its underlying allocation by transferring elements one by one.
593    ///
594    /// # Complexity
595    ///
596    /// - Time: O(n) where n is the number of elements
597    /// - Space: O(n) for the new allocation (original Vec allocation is dropped)
598    ///
599    /// # Examples
600    ///
601    /// ```rust
602    /// use certeza::TruenoVec;
603    ///
604    /// let std_vec = vec![1, 2, 3, 4, 5];
605    /// let trueno_vec: TruenoVec<i32> = TruenoVec::from(std_vec);
606    ///
607    /// assert_eq!(trueno_vec.len(), 5);
608    /// assert_eq!(trueno_vec.get(0), Some(&1));
609    /// assert_eq!(trueno_vec.get(4), Some(&5));
610    /// ```
611    fn from(vec: Vec<T>) -> Self {
612        let mut trueno = Self::with_capacity(vec.len());
613        for item in vec {
614            trueno.push(item);
615        }
616        trueno
617    }
618}
619
620impl<T: Clone> From<&[T]> for TruenoVec<T> {
621    /// Converts a slice `&[T]` into a `TruenoVec<T>`.
622    ///
623    /// This conversion clones all elements from the slice into a new `TruenoVec`.
624    /// Requires `T: Clone` since we're creating owned copies.
625    ///
626    /// # Complexity
627    ///
628    /// - Time: O(n) where n is the number of elements
629    /// - Space: O(n)
630    ///
631    /// # Examples
632    ///
633    /// ```rust
634    /// use certeza::TruenoVec;
635    ///
636    /// let array = [1, 2, 3, 4, 5];
637    /// let slice: &[i32] = &array;
638    /// let trueno_vec: TruenoVec<i32> = TruenoVec::from(slice);
639    ///
640    /// assert_eq!(trueno_vec.len(), 5);
641    /// assert_eq!(trueno_vec.get(2), Some(&3));
642    /// ```
643    fn from(slice: &[T]) -> Self {
644        let mut trueno = Self::with_capacity(slice.len());
645        for item in slice {
646            trueno.push(item.clone());
647        }
648        trueno
649    }
650}
651
652impl<T> FromIterator<T> for TruenoVec<T> {
653    /// Creates a `TruenoVec<T>` from an iterator.
654    ///
655    /// This enables the `.collect()` method on iterators to produce a `TruenoVec`.
656    ///
657    /// # Complexity
658    ///
659    /// - Time: O(n) where n is the number of elements in the iterator
660    /// - Space: O(n)
661    ///
662    /// # Examples
663    ///
664    /// ```rust
665    /// use certeza::TruenoVec;
666    ///
667    /// let trueno_vec: TruenoVec<i32> = (0..10).collect();
668    ///
669    /// assert_eq!(trueno_vec.len(), 10);
670    /// assert_eq!(trueno_vec.get(5), Some(&5));
671    /// ```
672    ///
673    /// ```rust
674    /// use certeza::TruenoVec;
675    ///
676    /// let numbers = vec![1, 2, 3, 4, 5];
677    /// let doubled: TruenoVec<i32> = numbers.iter().map(|x| x * 2).collect();
678    ///
679    /// assert_eq!(doubled.len(), 5);
680    /// assert_eq!(doubled.get(0), Some(&2));
681    /// assert_eq!(doubled.get(4), Some(&10));
682    /// ```
683    fn from_iter<I: IntoIterator<Item = T>>(iter: I) -> Self {
684        let iter = iter.into_iter();
685        let (lower_bound, _) = iter.size_hint();
686        let mut trueno = Self::with_capacity(lower_bound);
687
688        for item in iter {
689            trueno.push(item);
690        }
691
692        trueno
693    }
694}
695
696impl<T> Extend<T> for TruenoVec<T> {
697    /// Extends a `TruenoVec<T>` with the contents of an iterator.
698    ///
699    /// This method appends all elements from the iterator to the end of the vector.
700    ///
701    /// # Complexity
702    ///
703    /// - Time: O(n) where n is the number of elements in the iterator
704    /// - Space: O(n) amortized
705    ///
706    /// # Examples
707    ///
708    /// ```rust
709    /// use certeza::TruenoVec;
710    ///
711    /// let mut vec = TruenoVec::new();
712    /// vec.push(1);
713    /// vec.push(2);
714    ///
715    /// vec.extend(vec![3, 4, 5]);
716    ///
717    /// assert_eq!(vec.len(), 5);
718    /// assert_eq!(vec.get(0), Some(&1));
719    /// assert_eq!(vec.get(4), Some(&5));
720    /// ```
721    ///
722    /// ```rust
723    /// use certeza::TruenoVec;
724    ///
725    /// let mut vec = TruenoVec::new();
726    /// vec.extend(0..10);
727    ///
728    /// assert_eq!(vec.len(), 10);
729    /// ```
730    fn extend<I: IntoIterator<Item = T>>(&mut self, iter: I) {
731        let iter = iter.into_iter();
732        let (lower_bound, _) = iter.size_hint();
733
734        // Reserve space if we know the size hint
735        if lower_bound > 0 {
736            let needed_capacity = self.len.saturating_add(lower_bound);
737            while self.capacity < needed_capacity {
738                self.grow();
739            }
740        }
741
742        for item in iter {
743            self.push(item);
744        }
745    }
746}
747
748// ============================================================================
749// Iterator Implementations
750// ============================================================================
751
752/// Immutable iterator over `TruenoVec<T>`.
753///
754/// This struct is created by the `iter` method on `TruenoVec`.
755pub struct Iter<'a, T> {
756    ptr: *const T,
757    end: *const T,
758    _marker: PhantomData<&'a T>,
759}
760
761impl<'a, T> Iterator for Iter<'a, T> {
762    type Item = &'a T;
763
764    fn next(&mut self) -> Option<Self::Item> {
765        if self.ptr == self.end {
766            None
767        } else {
768            // SAFETY: ptr is valid and within bounds
769            unsafe {
770                let item = &*self.ptr;
771                self.ptr = self.ptr.add(1);
772                Some(item)
773            }
774        }
775    }
776
777    fn size_hint(&self) -> (usize, Option<usize>) {
778        let size = std::mem::size_of::<T>();
779        let len = if size == 0 { 0 } else { (self.end as usize - self.ptr as usize) / size };
780        (len, Some(len))
781    }
782}
783
784impl<T> ExactSizeIterator for Iter<'_, T> {}
785
786impl<T> DoubleEndedIterator for Iter<'_, T> {
787    fn next_back(&mut self) -> Option<Self::Item> {
788        if self.ptr == self.end {
789            None
790        } else {
791            // SAFETY: end-1 is valid and within bounds
792            unsafe {
793                self.end = self.end.sub(1);
794                Some(&*self.end)
795            }
796        }
797    }
798}
799
800/// Mutable iterator over `TruenoVec<T>`.
801///
802/// This struct is created by the `iter_mut` method on `TruenoVec`.
803pub struct IterMut<'a, T> {
804    ptr: *mut T,
805    end: *mut T,
806    _marker: PhantomData<&'a mut T>,
807}
808
809impl<'a, T> Iterator for IterMut<'a, T> {
810    type Item = &'a mut T;
811
812    fn next(&mut self) -> Option<Self::Item> {
813        if self.ptr == self.end {
814            None
815        } else {
816            // SAFETY: ptr is valid and within bounds
817            unsafe {
818                let item = &mut *self.ptr;
819                self.ptr = self.ptr.add(1);
820                Some(item)
821            }
822        }
823    }
824
825    fn size_hint(&self) -> (usize, Option<usize>) {
826        let size = std::mem::size_of::<T>();
827        let len = if size == 0 { 0 } else { (self.end as usize - self.ptr as usize) / size };
828        (len, Some(len))
829    }
830}
831
832impl<T> ExactSizeIterator for IterMut<'_, T> {}
833
834impl<T> DoubleEndedIterator for IterMut<'_, T> {
835    fn next_back(&mut self) -> Option<Self::Item> {
836        if self.ptr == self.end {
837            None
838        } else {
839            // SAFETY: end-1 is valid and within bounds
840            unsafe {
841                self.end = self.end.sub(1);
842                Some(&mut *self.end)
843            }
844        }
845    }
846}
847
848/// Consuming iterator over `TruenoVec<T>`.
849///
850/// This struct is created by the `into_iter` method on `TruenoVec`
851/// (provided by the `IntoIterator` trait).
852pub struct IntoIter<T> {
853    vec: TruenoVec<T>,
854    current: usize,
855}
856
857impl<T> Iterator for IntoIter<T> {
858    type Item = T;
859
860    fn next(&mut self) -> Option<Self::Item> {
861        if self.current < self.vec.len {
862            let index = self.current;
863            self.current += 1;
864            // SAFETY: index < len, so it's a valid initialized element
865            // We take ownership by reading, so the Drop impl won't try to drop it again
866            unsafe { Some(ptr::read(self.vec.ptr.as_ptr().add(index))) }
867        } else {
868            None
869        }
870    }
871
872    fn size_hint(&self) -> (usize, Option<usize>) {
873        let remaining = self.vec.len - self.current;
874        (remaining, Some(remaining))
875    }
876}
877
878impl<T> ExactSizeIterator for IntoIter<T> {}
879
880impl<T> Drop for IntoIter<T> {
881    fn drop(&mut self) {
882        // Drop all remaining unconsumed elements
883        while self.current < self.vec.len {
884            // SAFETY: current is bounded by vec.len, ptr is valid for vec.len elements
885            unsafe {
886                ptr::drop_in_place(self.vec.ptr.as_ptr().add(self.current));
887            }
888            self.current += 1;
889        }
890
891        // Now deallocate the memory (all elements have been dropped)
892        if self.vec.capacity > 0 {
893            let layout = Layout::array::<T>(self.vec.capacity).expect("capacity overflow");
894            // SAFETY: ptr was allocated with this layout and capacity > 0 guarantees valid alloc
895            unsafe {
896                alloc::dealloc(self.vec.ptr.as_ptr().cast::<u8>(), layout);
897            }
898        }
899
900        // Prevent the vec's Drop from running by setting capacity to 0
901        // This is safe because we've already handled deallocation
902        self.vec.capacity = 0;
903        self.vec.len = 0;
904    }
905}
906
907impl<T> TruenoVec<T> {
908    /// Returns an iterator over the vector.
909    ///
910    /// # Examples
911    ///
912    /// ```rust
913    /// use certeza::TruenoVec;
914    ///
915    /// let mut vec = TruenoVec::new();
916    /// vec.push(1);
917    /// vec.push(2);
918    /// vec.push(3);
919    ///
920    /// let mut iter = vec.iter();
921    /// assert_eq!(iter.next(), Some(&1));
922    /// assert_eq!(iter.next(), Some(&2));
923    /// assert_eq!(iter.next(), Some(&3));
924    /// assert_eq!(iter.next(), None);
925    /// ```
926    #[must_use]
927    pub const fn iter(&self) -> Iter<'_, T> {
928        // SAFETY: ptr and ptr+len are both valid
929        unsafe {
930            Iter {
931                ptr: self.ptr.as_ptr(),
932                end: self.ptr.as_ptr().add(self.len),
933                _marker: PhantomData,
934            }
935        }
936    }
937
938    /// Returns a mutable iterator over the vector.
939    ///
940    /// # Examples
941    ///
942    /// ```rust
943    /// use certeza::TruenoVec;
944    ///
945    /// let mut vec = TruenoVec::new();
946    /// vec.push(1);
947    /// vec.push(2);
948    /// vec.push(3);
949    ///
950    /// for elem in vec.iter_mut() {
951    ///     *elem *= 2;
952    /// }
953    ///
954    /// assert_eq!(vec.get(0), Some(&2));
955    /// assert_eq!(vec.get(1), Some(&4));
956    /// assert_eq!(vec.get(2), Some(&6));
957    /// ```
958    #[must_use]
959    pub const fn iter_mut(&mut self) -> IterMut<'_, T> {
960        // SAFETY: ptr and ptr+len are both valid
961        unsafe {
962            IterMut {
963                ptr: self.ptr.as_ptr(),
964                end: self.ptr.as_ptr().add(self.len),
965                _marker: PhantomData,
966            }
967        }
968    }
969}
970
971impl<T> IntoIterator for TruenoVec<T> {
972    type Item = T;
973    type IntoIter = IntoIter<T>;
974
975    /// Consumes the vector and returns an iterator over its elements.
976    ///
977    /// # Examples
978    ///
979    /// ```rust
980    /// use certeza::TruenoVec;
981    ///
982    /// let mut vec = TruenoVec::new();
983    /// vec.push(1);
984    /// vec.push(2);
985    /// vec.push(3);
986    ///
987    /// let sum: i32 = vec.into_iter().sum();
988    /// assert_eq!(sum, 6);
989    /// ```
990    fn into_iter(self) -> Self::IntoIter {
991        IntoIter { vec: self, current: 0 }
992    }
993}
994
995impl<'a, T> IntoIterator for &'a TruenoVec<T> {
996    type Item = &'a T;
997    type IntoIter = Iter<'a, T>;
998
999    fn into_iter(self) -> Self::IntoIter {
1000        self.iter()
1001    }
1002}
1003
1004impl<'a, T> IntoIterator for &'a mut TruenoVec<T> {
1005    type Item = &'a mut T;
1006    type IntoIter = IterMut<'a, T>;
1007
1008    fn into_iter(self) -> Self::IntoIter {
1009        self.iter_mut()
1010    }
1011}
1012
1013// ============================================================================
1014// Index Trait Implementations
1015// ============================================================================
1016
1017impl<T> std::ops::Index<usize> for TruenoVec<T> {
1018    type Output = T;
1019
1020    /// Returns a reference to an element at the given index.
1021    ///
1022    /// # Panics
1023    ///
1024    /// Panics if the index is out of bounds.
1025    ///
1026    /// # Examples
1027    ///
1028    /// ```
1029    /// use certeza::TruenoVec;
1030    ///
1031    /// let mut vec = TruenoVec::new();
1032    /// vec.push(10);
1033    /// vec.push(20);
1034    /// vec.push(30);
1035    ///
1036    /// assert_eq!(vec[0], 10);
1037    /// assert_eq!(vec[1], 20);
1038    /// assert_eq!(vec[2], 30);
1039    /// ```
1040    fn index(&self, index: usize) -> &Self::Output {
1041        let len = self.len;
1042        self.get(index).unwrap_or_else(|| {
1043            panic!("index out of bounds: the len is {len} but the index is {index}")
1044        })
1045    }
1046}
1047
1048impl<T> std::ops::IndexMut<usize> for TruenoVec<T> {
1049    /// Returns a mutable reference to an element at the given index.
1050    ///
1051    /// # Panics
1052    ///
1053    /// Panics if the index is out of bounds.
1054    ///
1055    /// # Examples
1056    ///
1057    /// ```
1058    /// use certeza::TruenoVec;
1059    ///
1060    /// let mut vec = TruenoVec::new();
1061    /// vec.push(10);
1062    /// vec.push(20);
1063    /// vec.push(30);
1064    ///
1065    /// vec[1] = 25;
1066    /// assert_eq!(vec[1], 25);
1067    /// ```
1068    fn index_mut(&mut self, index: usize) -> &mut Self::Output {
1069        let len = self.len;
1070        self.get_mut(index).unwrap_or_else(|| {
1071            panic!("index out of bounds: the len is {len} but the index is {index}")
1072        })
1073    }
1074}
1075
1076// ============================================================================
1077// Clone Trait Implementation
1078// ============================================================================
1079
1080impl<T: Clone> Clone for TruenoVec<T> {
1081    /// Creates a deep copy of the vector.
1082    ///
1083    /// # Examples
1084    ///
1085    /// ```
1086    /// use certeza::TruenoVec;
1087    ///
1088    /// let mut vec1 = TruenoVec::new();
1089    /// vec1.push(1);
1090    /// vec1.push(2);
1091    /// vec1.push(3);
1092    ///
1093    /// let mut vec2 = vec1.clone();
1094    ///
1095    /// // Modify vec2
1096    /// vec2.push(4);
1097    ///
1098    /// // vec1 is unchanged
1099    /// assert_eq!(vec1.len(), 3);
1100    /// assert_eq!(vec2.len(), 4);
1101    /// ```
1102    fn clone(&self) -> Self {
1103        let mut new_vec = Self::with_capacity(self.len);
1104        for elem in self {
1105            new_vec.push(elem.clone());
1106        }
1107        new_vec
1108    }
1109}
1110
1111// ============================================================================
1112// PartialEq and Eq Trait Implementations
1113// ============================================================================
1114
1115impl<T: PartialEq> PartialEq for TruenoVec<T> {
1116    /// Compares two vectors for equality.
1117    ///
1118    /// Two vectors are equal if they have the same length and all elements
1119    /// at corresponding indices are equal.
1120    ///
1121    /// # Examples
1122    ///
1123    /// ```
1124    /// use certeza::TruenoVec;
1125    ///
1126    /// let mut vec1 = TruenoVec::new();
1127    /// vec1.push(1);
1128    /// vec1.push(2);
1129    ///
1130    /// let mut vec2 = TruenoVec::new();
1131    /// vec2.push(1);
1132    /// vec2.push(2);
1133    ///
1134    /// assert_eq!(vec1, vec2);
1135    ///
1136    /// vec2.push(3);
1137    /// assert_ne!(vec1, vec2);
1138    /// ```
1139    fn eq(&self, other: &Self) -> bool {
1140        // First check lengths - fast path
1141        if self.len != other.len {
1142            return false;
1143        }
1144
1145        // Compare elements
1146        for i in 0..self.len {
1147            if self.get(i) != other.get(i) {
1148                return false;
1149            }
1150        }
1151
1152        true
1153    }
1154}
1155
1156impl<T: Eq> Eq for TruenoVec<T> {}
1157
1158// ============================================================================
1159// Debug Trait Implementation
1160// ============================================================================
1161
1162impl<T: std::fmt::Debug> std::fmt::Debug for TruenoVec<T> {
1163    /// Formats the vector for debugging output.
1164    ///
1165    /// # Examples
1166    ///
1167    /// ```
1168    /// use certeza::TruenoVec;
1169    ///
1170    /// let mut vec = TruenoVec::new();
1171    /// vec.push(1);
1172    /// vec.push(2);
1173    /// vec.push(3);
1174    ///
1175    /// assert_eq!(format!("{:?}", vec), "[1, 2, 3]");
1176    /// ```
1177    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1178        f.debug_list().entries(self.iter()).finish()
1179    }
1180}
1181
1182// ============================================================================
1183// Phase 3.1 Ergonomic Trait Implementations (Deref/AsRef)
1184// ============================================================================
1185
1186impl<T> std::ops::Deref for TruenoVec<T> {
1187    type Target = [T];
1188
1189    /// Dereferences the `TruenoVec<T>` to a slice `&[T]`.
1190    ///
1191    /// This allows `TruenoVec` to be used seamlessly with any function
1192    /// that accepts a slice, enabling automatic coercion and access to
1193    /// all slice methods.
1194    ///
1195    /// # Examples
1196    ///
1197    /// ```
1198    /// use certeza::TruenoVec;
1199    ///
1200    /// let mut vec = TruenoVec::new();
1201    /// vec.push(1);
1202    /// vec.push(2);
1203    /// vec.push(3);
1204    ///
1205    /// // Deref coercion allows slice methods
1206    /// assert_eq!(vec.len(), 3);
1207    /// assert_eq!(vec.first(), Some(&1));
1208    /// assert_eq!(vec.last(), Some(&3));
1209    ///
1210    /// // Works with functions expecting slices
1211    /// fn sum_slice(s: &[i32]) -> i32 {
1212    ///     s.iter().sum()
1213    /// }
1214    /// assert_eq!(sum_slice(&vec), 6);
1215    /// ```
1216    fn deref(&self) -> &Self::Target {
1217        self.as_slice()
1218    }
1219}
1220
1221impl<T> std::ops::DerefMut for TruenoVec<T> {
1222    /// Mutably dereferences the `TruenoVec<T>` to a mutable slice `&mut [T]`.
1223    ///
1224    /// This allows mutable access to slice methods through deref coercion.
1225    ///
1226    /// # Examples
1227    ///
1228    /// ```
1229    /// use certeza::TruenoVec;
1230    ///
1231    /// let mut vec = TruenoVec::new();
1232    /// vec.push(3);
1233    /// vec.push(1);
1234    /// vec.push(2);
1235    ///
1236    /// // DerefMut coercion allows mutable slice methods
1237    /// vec.sort();
1238    /// assert_eq!(vec.as_slice(), &[1, 2, 3]);
1239    ///
1240    /// vec.reverse();
1241    /// assert_eq!(vec.as_slice(), &[3, 2, 1]);
1242    /// ```
1243    fn deref_mut(&mut self) -> &mut Self::Target {
1244        self.as_slice_mut()
1245    }
1246}
1247
1248impl<T> AsRef<[T]> for TruenoVec<T> {
1249    /// Returns a reference to the vector's contents as a slice.
1250    ///
1251    /// This enables `TruenoVec` to be used with generic functions that
1252    /// accept `AsRef<[T]>` bounds, a common pattern in the Rust standard library.
1253    ///
1254    /// # Examples
1255    ///
1256    /// ```
1257    /// use certeza::TruenoVec;
1258    ///
1259    /// let mut vec = TruenoVec::new();
1260    /// vec.push(1);
1261    /// vec.push(2);
1262    /// vec.push(3);
1263    ///
1264    /// // Works with generic functions using AsRef<[T]>
1265    /// fn process<T: AsRef<[i32]>>(data: T) -> i32 {
1266    ///     data.as_ref().iter().sum()
1267    /// }
1268    ///
1269    /// assert_eq!(process(&vec), 6);
1270    /// assert_eq!(process(vec![1, 2, 3]), 6);
1271    /// ```
1272    fn as_ref(&self) -> &[T] {
1273        self.as_slice()
1274    }
1275}
1276
1277impl<T> AsMut<[T]> for TruenoVec<T> {
1278    /// Returns a mutable reference to the vector's contents as a slice.
1279    ///
1280    /// This enables `TruenoVec` to be used with generic functions that
1281    /// accept `AsMut<[T]>` bounds, enabling mutable slice operations.
1282    ///
1283    /// # Examples
1284    ///
1285    /// ```
1286    /// use certeza::TruenoVec;
1287    ///
1288    /// let mut vec = TruenoVec::new();
1289    /// vec.push(1);
1290    /// vec.push(2);
1291    /// vec.push(3);
1292    ///
1293    /// // Works with generic functions using AsMut<[T]>
1294    /// fn double_in_place<T: AsMut<[i32]>>(mut data: T) {
1295    ///     for x in data.as_mut() {
1296    ///         *x *= 2;
1297    ///     }
1298    /// }
1299    ///
1300    /// double_in_place(&mut vec);
1301    /// assert_eq!(vec.as_slice(), &[2, 4, 6]);
1302    /// ```
1303    fn as_mut(&mut self) -> &mut [T] {
1304        self.as_slice_mut()
1305    }
1306}
1307
1308impl<T> AsRef<Self> for TruenoVec<T> {
1309    /// Returns a reference to self.
1310    ///
1311    /// This implementation allows `TruenoVec` to work with APIs that
1312    /// require `AsRef<TruenoVec<T>>`.
1313    ///
1314    /// # Examples
1315    ///
1316    /// ```
1317    /// use certeza::TruenoVec;
1318    ///
1319    /// let vec = TruenoVec::from(vec![1, 2, 3]);
1320    /// let vec_ref: &TruenoVec<i32> = vec.as_ref();
1321    /// assert_eq!(vec_ref.len(), 3);
1322    /// ```
1323    fn as_ref(&self) -> &Self {
1324        self
1325    }
1326}
1327
1328impl<T> AsMut<Self> for TruenoVec<T> {
1329    /// Returns a mutable reference to self.
1330    ///
1331    /// This implementation allows `TruenoVec` to work with APIs that
1332    /// require `AsMut<TruenoVec<T>>`.
1333    ///
1334    /// # Examples
1335    ///
1336    /// ```
1337    /// use certeza::TruenoVec;
1338    ///
1339    /// let mut vec = TruenoVec::from(vec![1, 2, 3]);
1340    /// let vec_mut: &mut TruenoVec<i32> = vec.as_mut();
1341    /// vec_mut.push(4);
1342    /// assert_eq!(vec_mut.len(), 4);
1343    /// ```
1344    fn as_mut(&mut self) -> &mut Self {
1345        self
1346    }
1347}
1348
1349// ============================================================================
1350// Phase 3.2 Comparison and Hash Trait Implementations
1351// ============================================================================
1352
1353impl<T: PartialOrd> PartialOrd for TruenoVec<T> {
1354    /// Compares two vectors lexicographically.
1355    ///
1356    /// Vectors are compared element-by-element from left to right.
1357    /// The first mismatching element determines the ordering.
1358    /// If all elements match but one vector is shorter, the shorter vector is less.
1359    ///
1360    /// # Examples
1361    ///
1362    /// ```
1363    /// use certeza::TruenoVec;
1364    ///
1365    /// let mut vec1 = TruenoVec::new();
1366    /// vec1.push(1);
1367    /// vec1.push(2);
1368    ///
1369    /// let mut vec2 = TruenoVec::new();
1370    /// vec2.push(1);
1371    /// vec2.push(3);
1372    ///
1373    /// assert!(vec1 < vec2);
1374    /// assert!(vec2 > vec1);
1375    ///
1376    /// let mut vec3 = TruenoVec::new();
1377    /// vec3.push(1);
1378    /// assert!(vec3 < vec1); // Shorter vector is less
1379    /// ```
1380    fn partial_cmp(&self, other: &Self) -> Option<std::cmp::Ordering> {
1381        self.as_slice().partial_cmp(other.as_slice())
1382    }
1383
1384    fn lt(&self, other: &Self) -> bool {
1385        self.as_slice() < other.as_slice()
1386    }
1387
1388    fn le(&self, other: &Self) -> bool {
1389        self.as_slice() <= other.as_slice()
1390    }
1391
1392    fn gt(&self, other: &Self) -> bool {
1393        self.as_slice() > other.as_slice()
1394    }
1395
1396    fn ge(&self, other: &Self) -> bool {
1397        self.as_slice() >= other.as_slice()
1398    }
1399}
1400
1401impl<T: Ord> Ord for TruenoVec<T> {
1402    /// Returns the total ordering between two vectors.
1403    ///
1404    /// This provides a total ordering for vectors where `T: Ord`,
1405    /// enabling use in `BTreeMap` and `BTreeSet` as keys, and
1406    /// allowing sorting of vectors.
1407    ///
1408    /// # Examples
1409    ///
1410    /// ```
1411    /// use certeza::TruenoVec;
1412    /// use std::cmp::Ordering;
1413    ///
1414    /// let mut vec1 = TruenoVec::new();
1415    /// vec1.push(1);
1416    /// vec1.push(2);
1417    ///
1418    /// let mut vec2 = TruenoVec::new();
1419    /// vec2.push(1);
1420    /// vec2.push(3);
1421    ///
1422    /// assert_eq!(vec1.cmp(&vec2), Ordering::Less);
1423    ///
1424    /// // Can be used for sorting
1425    /// let mut vecs = vec![vec2.clone(), vec1.clone()];
1426    /// vecs.sort();
1427    /// assert_eq!(vecs[0], vec1);
1428    /// assert_eq!(vecs[1], vec2);
1429    /// ```
1430    fn cmp(&self, other: &Self) -> std::cmp::Ordering {
1431        self.as_slice().cmp(other.as_slice())
1432    }
1433}
1434
1435impl<T: std::hash::Hash> std::hash::Hash for TruenoVec<T> {
1436    /// Hashes the vector by hashing all its elements in order.
1437    ///
1438    /// This enables `TruenoVec` to be used as keys in `HashMap` and
1439    /// values in `HashSet`, provided `T: Hash`.
1440    ///
1441    /// # Examples
1442    ///
1443    /// ```
1444    /// use certeza::TruenoVec;
1445    /// use std::collections::HashMap;
1446    ///
1447    /// let mut map = HashMap::new();
1448    ///
1449    /// let mut key = TruenoVec::new();
1450    /// key.push(1);
1451    /// key.push(2);
1452    /// key.push(3);
1453    ///
1454    /// map.insert(key.clone(), "value");
1455    /// assert_eq!(map.get(&key), Some(&"value"));
1456    ///
1457    /// // Different vectors have different hashes
1458    /// let mut key2 = TruenoVec::new();
1459    /// key2.push(1);
1460    /// key2.push(2);
1461    /// assert_eq!(map.get(&key2), None);
1462    /// ```
1463    fn hash<H: std::hash::Hasher>(&self, state: &mut H) {
1464        // Hash the length first (same as std::Vec)
1465        self.len.hash(state);
1466        // Hash each element
1467        for elem in self {
1468            elem.hash(state);
1469        }
1470    }
1471}
1472
1473// ============================================================================
1474// Phase 3.3: Display and Borrow Traits (Polish & Advanced Use Cases)
1475// ============================================================================
1476
1477/// Display trait for user-friendly formatting
1478///
1479/// Formats the vector as `[elem1, elem2, ...]` similar to `std::Vec`.
1480///
1481/// # Examples
1482///
1483/// ```
1484/// use certeza::TruenoVec;
1485///
1486/// let vec = TruenoVec::from(vec![1, 2, 3]);
1487/// assert_eq!(format!("{}", vec), "[1, 2, 3]");
1488/// ```
1489impl<T: std::fmt::Display> std::fmt::Display for TruenoVec<T> {
1490    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1491        write!(f, "[")?;
1492        for (i, elem) in self.iter().enumerate() {
1493            if i > 0 {
1494                write!(f, ", ")?;
1495            }
1496            write!(f, "{elem}")?;
1497        }
1498        write!(f, "]")
1499    }
1500}
1501
1502/// Borrow<[T]> trait for advanced borrowing patterns
1503///
1504/// Enables using `TruenoVec` with APIs that accept `Borrow<[T]>` bounds,
1505/// particularly useful for `HashMap` and `BTreeMap` lookups.
1506///
1507/// # Examples
1508///
1509/// ```
1510/// use certeza::TruenoVec;
1511/// use std::borrow::Borrow;
1512///
1513/// let vec = TruenoVec::from(vec![1, 2, 3]);
1514/// let slice: &[i32] = vec.borrow();
1515/// assert_eq!(slice, &[1, 2, 3]);
1516/// ```
1517impl<T> std::borrow::Borrow<[T]> for TruenoVec<T> {
1518    fn borrow(&self) -> &[T] {
1519        self.as_slice()
1520    }
1521}
1522
1523/// `BorrowMut<[T]>` trait for advanced mutable borrowing patterns
1524///
1525/// Enables using `TruenoVec` with APIs that accept `BorrowMut<[T]>` bounds.
1526///
1527/// # Examples
1528///
1529/// ```
1530/// use certeza::TruenoVec;
1531/// use std::borrow::BorrowMut;
1532///
1533/// let mut vec = TruenoVec::from(vec![1, 2, 3]);
1534/// let slice: &mut [i32] = vec.borrow_mut();
1535/// slice[0] = 10;
1536/// assert_eq!(vec.get(0), Some(&10));
1537/// ```
1538impl<T> std::borrow::BorrowMut<[T]> for TruenoVec<T> {
1539    fn borrow_mut(&mut self) -> &mut [T] {
1540        self.as_slice_mut()
1541    }
1542}
1543
1544// ============================================================================
1545// Unit Tests (Tier 1: Sub-second feedback)
1546// ============================================================================
1547
1548#[cfg(test)]
1549#[path = "tests.rs"]
1550mod vec_tests;
1551
1552#[cfg(test)]
1553#[path = "property_tests.rs"]
1554mod vec_property_tests;