1#![allow(unused_variables)]
2#![allow(missing_docs)]
3
4use super::*;
5
6pub struct SliceVec<'s, T> {
17 data: &'s mut [T],
18 len: usize,
19}
20
21impl<'s, T> Default for SliceVec<'s, T> {
22 #[inline(always)]
23 fn default() -> Self {
24 Self { data: &mut [], len: 0 }
25 }
26}
27
28impl<'s, T> Deref for SliceVec<'s, T> {
29 type Target = [T];
30 #[inline(always)]
31 fn deref(&self) -> &Self::Target {
32 &self.data[..self.len]
33 }
34}
35
36impl<'s, T> DerefMut for SliceVec<'s, T> {
37 #[inline(always)]
38 fn deref_mut(&mut self) -> &mut Self::Target {
39 &mut self.data[..self.len]
40 }
41}
42
43impl<'s, T, I> Index<I> for SliceVec<'s, T>
44where
45 I: SliceIndex<[T]>,
46{
47 type Output = <I as SliceIndex<[T]>>::Output;
48 #[inline(always)]
49 fn index(&self, index: I) -> &Self::Output {
50 &self.deref()[index]
51 }
52}
53
54impl<'s, T, I> IndexMut<I> for SliceVec<'s, T>
55where
56 I: SliceIndex<[T]>,
57{
58 #[inline(always)]
59 fn index_mut(&mut self, index: I) -> &mut Self::Output {
60 &mut self.deref_mut()[index]
61 }
62}
63
64impl<'s, T> SliceVec<'s, T> {
65 #[inline]
66 pub fn append(&mut self, other: &mut Self)
67 where
68 T: Default,
69 {
70 for item in other.drain(..) {
71 self.push(item)
72 }
73 }
74
75 #[inline(always)]
81 #[must_use]
82 pub fn as_mut_ptr(&mut self) -> *mut T {
83 self.data.as_mut_ptr()
84 }
85
86 #[inline(always)]
88 #[must_use]
89 pub fn as_mut_slice(&mut self) -> &mut [T] {
90 self.deref_mut()
91 }
92
93 #[inline(always)]
99 #[must_use]
100 pub fn as_ptr(&self) -> *const T {
101 self.data.as_ptr()
102 }
103
104 #[inline(always)]
106 #[must_use]
107 pub fn as_slice(&self) -> &[T] {
108 self.deref()
109 }
110
111 #[inline(always)]
115 #[must_use]
116 pub fn capacity(&self) -> usize {
117 self.data.len()
118 }
119
120 #[inline(always)]
122 pub fn clear(&mut self)
123 where
124 T: Default,
125 {
126 self.truncate(0)
127 }
128
129 #[inline]
149 pub fn drain<'p, R: RangeBounds<usize>>(
150 &'p mut self, range: R,
151 ) -> SliceVecDrain<'p, 's, T>
152 where
153 T: Default,
154 {
155 use core::ops::Bound;
156 let start = match range.start_bound() {
157 Bound::Included(x) => *x,
158 Bound::Excluded(x) => x.saturating_add(1),
159 Bound::Unbounded => 0,
160 };
161 let end = match range.end_bound() {
162 Bound::Included(x) => x.saturating_add(1),
163 Bound::Excluded(x) => *x,
164 Bound::Unbounded => self.len,
165 };
166 assert!(
167 start <= end,
168 "SliceVec::drain> Illegal range, {} to {}",
169 start,
170 end
171 );
172 assert!(
173 end <= self.len,
174 "SliceVec::drain> Range ends at {} but length is only {}!",
175 end,
176 self.len
177 );
178 SliceVecDrain {
179 parent: self,
180 target_start: start,
181 target_index: start,
182 target_end: end,
183 }
184 }
185
186 #[inline]
187 pub fn extend_from_slice(&mut self, sli: &[T])
188 where
189 T: Clone,
190 {
191 if sli.is_empty() {
192 return;
193 }
194
195 let new_len = self.len + sli.len();
196 if new_len > self.capacity() {
197 panic!(
198 "SliceVec::extend_from_slice> total length {} exceeds capacity {}",
199 new_len,
200 self.capacity()
201 )
202 }
203
204 let target = &mut self.data[self.len..new_len];
205 target.clone_from_slice(sli);
206 self.set_len(new_len);
207 }
208
209 #[inline]
236 pub fn fill<I: IntoIterator<Item = T>>(&mut self, iter: I) -> I::IntoIter {
237 let mut iter = iter.into_iter();
238 for element in iter.by_ref().take(self.capacity() - self.len()) {
239 self.push(element);
240 }
241 iter
242 }
243
244 #[inline]
253 #[must_use]
254 #[allow(clippy::match_wild_err_arm)]
255 pub fn from_slice_len(data: &'s mut [T], len: usize) -> Self {
256 assert!(len <= data.len());
257 Self { data, len }
258 }
259
260 #[inline]
278 pub fn insert(&mut self, index: usize, item: T) {
279 if index > self.len {
280 panic!("SliceVec::insert> index {} is out of bounds {}", index, self.len);
281 }
282
283 self.push(item);
285 self.as_mut_slice()[index..].rotate_right(1);
287 }
288
289 #[inline(always)]
291 #[must_use]
292 pub fn is_empty(&self) -> bool {
293 self.len == 0
294 }
295
296 #[inline(always)]
298 #[must_use]
299 pub fn is_full(&self) -> bool {
300 self.len() == self.capacity()
301 }
302
303 #[inline(always)]
305 #[must_use]
306 pub fn len(&self) -> usize {
307 self.len
308 }
309
310 #[inline]
325 pub fn pop(&mut self) -> Option<T>
326 where
327 T: Default,
328 {
329 if self.len > 0 {
330 self.len -= 1;
331 let out = core::mem::take(&mut self.data[self.len]);
332 Some(out)
333 } else {
334 None
335 }
336 }
337
338 #[inline(always)]
356 pub fn push(&mut self, val: T) {
357 if self.len < self.capacity() {
358 self.data[self.len] = val;
359 self.len += 1;
360 } else {
361 panic!("SliceVec::push> capacity overflow")
362 }
363 }
364
365 #[inline]
383 pub fn remove(&mut self, index: usize) -> T
384 where
385 T: Default,
386 {
387 let targets: &mut [T] = &mut self.deref_mut()[index..];
388 let item = core::mem::take(&mut targets[0]);
389 targets.rotate_left(1);
390 self.len -= 1;
391 item
392 }
393
394 #[inline]
414 pub fn resize(&mut self, new_len: usize, new_val: T)
415 where
416 T: Clone,
417 {
418 self.resize_with(new_len, || new_val.clone())
419 }
420
421 #[inline]
448 pub fn resize_with<F: FnMut() -> T>(&mut self, new_len: usize, mut f: F) {
449 match new_len.checked_sub(self.len) {
450 None => {
451 if needs_drop::<T>() {
452 while self.len() > new_len {
453 self.len -= 1;
454 self.data[self.len] = f();
455 }
456 } else {
457 self.len = new_len;
458 }
459 }
460 Some(new_elements) => {
461 for _ in 0..new_elements {
462 self.push(f());
463 }
464 }
465 }
466 }
467
468 #[inline]
481 pub fn retain<F: FnMut(&T) -> bool>(&mut self, mut acceptable: F)
482 where
483 T: Default,
484 {
485 struct JoinOnDrop<'vec, Item> {
488 items: &'vec mut [Item],
489 done_end: usize,
490 tail_start: usize,
492 }
493
494 impl<Item> Drop for JoinOnDrop<'_, Item> {
495 fn drop(&mut self) {
496 self.items[self.done_end..].rotate_left(self.tail_start);
497 }
498 }
499
500 let mut rest = JoinOnDrop { items: self.data, done_end: 0, tail_start: 0 };
501
502 for idx in 0..self.len {
503 if !acceptable(&rest.items[idx]) {
505 let _ = core::mem::take(&mut rest.items[idx]);
506 self.len -= 1;
507 rest.tail_start += 1;
508 } else {
509 rest.items.swap(rest.done_end, idx);
510 rest.done_end += 1;
511 }
512 }
513 }
514
515 #[inline(always)]
526 pub fn set_len(&mut self, new_len: usize) {
527 if new_len > self.capacity() {
528 panic!(
533 "SliceVec::set_len> new length {} exceeds capacity {}",
534 new_len,
535 self.capacity()
536 )
537 } else {
538 self.len = new_len;
539 }
540 }
541
542 #[inline]
561 pub fn split_off<'a>(&'a mut self, at: usize) -> SliceVec<'s, T> {
562 let mut new = Self::default();
563 let backing: &'s mut [T] = core::mem::take(&mut self.data);
564 let (me, other) = backing.split_at_mut(at);
565 new.len = self.len - at;
566 new.data = other;
567 self.len = me.len();
568 self.data = me;
569 new
570 }
571
572 #[inline]
590 pub fn swap_remove(&mut self, index: usize) -> T
591 where
592 T: Default,
593 {
594 assert!(
595 index < self.len,
596 "SliceVec::swap_remove> index {} is out of bounds {}",
597 index,
598 self.len
599 );
600 if index == self.len - 1 {
601 self.pop().unwrap()
602 } else {
603 let i = self.pop().unwrap();
604 replace(&mut self[index], i)
605 }
606 }
607
608 #[inline]
612 pub fn truncate(&mut self, new_len: usize)
613 where
614 T: Default,
615 {
616 if needs_drop::<T>() {
617 while self.len > new_len {
618 self.pop();
619 }
620 } else {
621 self.len = self.len.min(new_len);
622 }
623 }
624
625 #[inline]
635 pub fn try_from_slice_len(data: &'s mut [T], len: usize) -> Option<Self> {
636 if len <= data.len() {
637 Some(Self { data, len })
638 } else {
639 None
640 }
641 }
642}
643
644impl<'s, T> SliceVec<'s, T> {
645 #[inline(always)]
650 #[must_use]
651 pub const fn as_inner(&self) -> &[T] {
652 &*self.data
653 }
654
655 #[inline(always)]
660 #[must_use]
661 #[cfg(feature = "latest_stable_rust")]
662 pub const fn as_mut_inner(&mut self) -> &mut [T] {
663 self.data
664 }
665}
666
667#[cfg(feature = "grab_spare_slice")]
668impl<'s, T> SliceVec<'s, T> {
669 #[must_use]
684 #[inline(always)]
685 pub fn grab_spare_slice(&self) -> &[T] {
686 &self.data[self.len..]
687 }
688
689 #[inline(always)]
702 pub fn grab_spare_slice_mut(&mut self) -> &mut [T] {
703 &mut self.data[self.len..]
704 }
705}
706
707impl<'s, T> From<&'s mut [T]> for SliceVec<'s, T> {
708 #[inline]
716 fn from(data: &'s mut [T]) -> Self {
717 let len = data.len();
718 Self { data, len }
719 }
720}
721
722impl<'s, T, A> From<&'s mut A> for SliceVec<'s, T>
723where
724 A: AsMut<[T]>,
725{
726 #[inline]
734 fn from(a: &'s mut A) -> Self {
735 let data = a.as_mut();
736 let len = data.len();
737 Self { data, len }
738 }
739}
740
741pub struct SliceVecDrain<'p, 's, T: Default> {
745 parent: &'p mut SliceVec<'s, T>,
746 target_start: usize,
747 target_index: usize,
748 target_end: usize,
749}
750impl<'p, 's, T: Default> Iterator for SliceVecDrain<'p, 's, T> {
751 type Item = T;
752 #[inline]
753 fn next(&mut self) -> Option<Self::Item> {
754 if self.target_index != self.target_end {
755 let out = core::mem::take(&mut self.parent[self.target_index]);
756 self.target_index += 1;
757 Some(out)
758 } else {
759 None
760 }
761 }
762}
763impl<'p, 's, T: Default> FusedIterator for SliceVecDrain<'p, 's, T> {}
764impl<'p, 's, T: Default> Drop for SliceVecDrain<'p, 's, T> {
765 #[inline]
766 fn drop(&mut self) {
767 self.for_each(drop);
770 let count = self.target_end - self.target_start;
772 let targets: &mut [T] = &mut self.parent.deref_mut()[self.target_start..];
773 targets.rotate_left(count);
774 self.parent.len -= count;
775 }
776}
777
778impl<'s, T> AsMut<[T]> for SliceVec<'s, T> {
779 #[inline(always)]
780 fn as_mut(&mut self) -> &mut [T] {
781 &mut *self
782 }
783}
784
785impl<'s, T> AsRef<[T]> for SliceVec<'s, T> {
786 #[inline(always)]
787 fn as_ref(&self) -> &[T] {
788 &*self
789 }
790}
791
792impl<'s, T> Borrow<[T]> for SliceVec<'s, T> {
793 #[inline(always)]
794 fn borrow(&self) -> &[T] {
795 &*self
796 }
797}
798
799impl<'s, T> BorrowMut<[T]> for SliceVec<'s, T> {
800 #[inline(always)]
801 fn borrow_mut(&mut self) -> &mut [T] {
802 &mut *self
803 }
804}
805
806impl<'s, T> Extend<T> for SliceVec<'s, T> {
807 #[inline]
808 fn extend<I: IntoIterator<Item = T>>(&mut self, iter: I) {
809 for t in iter {
810 self.push(t)
811 }
812 }
813}
814
815impl<'s, T> IntoIterator for SliceVec<'s, T> {
816 type Item = &'s mut T;
817 type IntoIter = core::slice::IterMut<'s, T>;
818 #[inline(always)]
819 fn into_iter(self) -> Self::IntoIter {
820 self.data.iter_mut()
821 }
822}
823
824impl<'s, T> PartialEq for SliceVec<'s, T>
825where
826 T: PartialEq,
827{
828 #[inline]
829 fn eq(&self, other: &Self) -> bool {
830 self.as_slice().eq(other.as_slice())
831 }
832}
833impl<'s, T> Eq for SliceVec<'s, T> where T: Eq {}
834
835impl<'s, T> PartialOrd for SliceVec<'s, T>
836where
837 T: PartialOrd,
838{
839 #[inline]
840 fn partial_cmp(&self, other: &Self) -> Option<core::cmp::Ordering> {
841 self.as_slice().partial_cmp(other.as_slice())
842 }
843}
844impl<'s, T> Ord for SliceVec<'s, T>
845where
846 T: Ord,
847{
848 #[inline]
849 fn cmp(&self, other: &Self) -> core::cmp::Ordering {
850 self.as_slice().cmp(other.as_slice())
851 }
852}
853
854impl<'s, T> PartialEq<&[T]> for SliceVec<'s, T>
855where
856 T: PartialEq,
857{
858 #[inline]
859 fn eq(&self, other: &&[T]) -> bool {
860 self.as_slice().eq(*other)
861 }
862}
863
864impl<'s, T> Hash for SliceVec<'s, T>
865where
866 T: Hash,
867{
868 #[inline]
869 fn hash<H: Hasher>(&self, state: &mut H) {
870 self.as_slice().hash(state)
871 }
872}
873
874#[cfg(feature = "experimental_write_impl")]
875impl<'s> core::fmt::Write for SliceVec<'s, u8> {
876 fn write_str(&mut self, s: &str) -> core::fmt::Result {
877 let my_len = self.len();
878 let str_len = s.as_bytes().len();
879 if my_len + str_len <= self.capacity() {
880 let remainder = &mut self.data[my_len..];
881 let target = &mut remainder[..str_len];
882 target.copy_from_slice(s.as_bytes());
883 Ok(())
884 } else {
885 Err(core::fmt::Error)
886 }
887 }
888}
889
890impl<'s, T> Binary for SliceVec<'s, T>
895where
896 T: Binary,
897{
898 #[allow(clippy::missing_inline_in_public_items)]
899 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
900 write!(f, "[")?;
901 if f.alternate() {
902 write!(f, "\n ")?;
903 }
904 for (i, elem) in self.iter().enumerate() {
905 if i > 0 {
906 write!(f, ",{}", if f.alternate() { "\n " } else { " " })?;
907 }
908 Binary::fmt(elem, f)?;
909 }
910 if f.alternate() {
911 write!(f, ",\n")?;
912 }
913 write!(f, "]")
914 }
915}
916
917impl<'s, T> Debug for SliceVec<'s, T>
918where
919 T: Debug,
920{
921 #[allow(clippy::missing_inline_in_public_items)]
922 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
923 <[T] as Debug>::fmt(self.as_slice(), f)
924 }
925}
926
927#[cfg(feature = "defmt")]
928#[cfg_attr(docs_rs, doc(cfg(feature = "defmt")))]
929impl<'s, T> defmt::Format for SliceVec<'s, T>
930where
931 T: defmt::Format,
932{
933 fn format(&self, fmt: defmt::Formatter<'_>) {
934 defmt::Format::format(self.as_slice(), fmt)
935 }
936}
937
938impl<'s, T> Display for SliceVec<'s, T>
939where
940 T: Display,
941{
942 #[allow(clippy::missing_inline_in_public_items)]
943 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
944 write!(f, "[")?;
945 if f.alternate() {
946 write!(f, "\n ")?;
947 }
948 for (i, elem) in self.iter().enumerate() {
949 if i > 0 {
950 write!(f, ",{}", if f.alternate() { "\n " } else { " " })?;
951 }
952 Display::fmt(elem, f)?;
953 }
954 if f.alternate() {
955 write!(f, ",\n")?;
956 }
957 write!(f, "]")
958 }
959}
960
961impl<'s, T> LowerExp for SliceVec<'s, T>
962where
963 T: LowerExp,
964{
965 #[allow(clippy::missing_inline_in_public_items)]
966 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
967 write!(f, "[")?;
968 if f.alternate() {
969 write!(f, "\n ")?;
970 }
971 for (i, elem) in self.iter().enumerate() {
972 if i > 0 {
973 write!(f, ",{}", if f.alternate() { "\n " } else { " " })?;
974 }
975 LowerExp::fmt(elem, f)?;
976 }
977 if f.alternate() {
978 write!(f, ",\n")?;
979 }
980 write!(f, "]")
981 }
982}
983
984impl<'s, T> LowerHex for SliceVec<'s, T>
985where
986 T: LowerHex,
987{
988 #[allow(clippy::missing_inline_in_public_items)]
989 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
990 write!(f, "[")?;
991 if f.alternate() {
992 write!(f, "\n ")?;
993 }
994 for (i, elem) in self.iter().enumerate() {
995 if i > 0 {
996 write!(f, ",{}", if f.alternate() { "\n " } else { " " })?;
997 }
998 LowerHex::fmt(elem, f)?;
999 }
1000 if f.alternate() {
1001 write!(f, ",\n")?;
1002 }
1003 write!(f, "]")
1004 }
1005}
1006
1007impl<'s, T> Octal for SliceVec<'s, T>
1008where
1009 T: Octal,
1010{
1011 #[allow(clippy::missing_inline_in_public_items)]
1012 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
1013 write!(f, "[")?;
1014 if f.alternate() {
1015 write!(f, "\n ")?;
1016 }
1017 for (i, elem) in self.iter().enumerate() {
1018 if i > 0 {
1019 write!(f, ",{}", if f.alternate() { "\n " } else { " " })?;
1020 }
1021 Octal::fmt(elem, f)?;
1022 }
1023 if f.alternate() {
1024 write!(f, ",\n")?;
1025 }
1026 write!(f, "]")
1027 }
1028}
1029
1030impl<'s, T> Pointer for SliceVec<'s, T>
1031where
1032 T: Pointer,
1033{
1034 #[allow(clippy::missing_inline_in_public_items)]
1035 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
1036 write!(f, "[")?;
1037 if f.alternate() {
1038 write!(f, "\n ")?;
1039 }
1040 for (i, elem) in self.iter().enumerate() {
1041 if i > 0 {
1042 write!(f, ",{}", if f.alternate() { "\n " } else { " " })?;
1043 }
1044 Pointer::fmt(elem, f)?;
1045 }
1046 if f.alternate() {
1047 write!(f, ",\n")?;
1048 }
1049 write!(f, "]")
1050 }
1051}
1052
1053impl<'s, T> UpperExp for SliceVec<'s, T>
1054where
1055 T: UpperExp,
1056{
1057 #[allow(clippy::missing_inline_in_public_items)]
1058 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
1059 write!(f, "[")?;
1060 if f.alternate() {
1061 write!(f, "\n ")?;
1062 }
1063 for (i, elem) in self.iter().enumerate() {
1064 if i > 0 {
1065 write!(f, ",{}", if f.alternate() { "\n " } else { " " })?;
1066 }
1067 UpperExp::fmt(elem, f)?;
1068 }
1069 if f.alternate() {
1070 write!(f, ",\n")?;
1071 }
1072 write!(f, "]")
1073 }
1074}
1075
1076impl<'s, T> UpperHex for SliceVec<'s, T>
1077where
1078 T: UpperHex,
1079{
1080 #[allow(clippy::missing_inline_in_public_items)]
1081 fn fmt(&self, f: &mut Formatter) -> core::fmt::Result {
1082 write!(f, "[")?;
1083 if f.alternate() {
1084 write!(f, "\n ")?;
1085 }
1086 for (i, elem) in self.iter().enumerate() {
1087 if i > 0 {
1088 write!(f, ",{}", if f.alternate() { "\n " } else { " " })?;
1089 }
1090 UpperHex::fmt(elem, f)?;
1091 }
1092 if f.alternate() {
1093 write!(f, ",\n")?;
1094 }
1095 write!(f, "]")
1096 }
1097}
1098
1099#[cfg(test)]
1100mod test {
1101 use super::*;
1102
1103 #[cfg(feature = "alloc")]
1104 #[test]
1105 fn array_like_debug() {
1106 #[derive(Debug, Default, Copy, Clone)]
1107 struct S {
1108 x: u8,
1109 y: u8,
1110 }
1111
1112 use core::fmt::Write;
1113
1114 let mut ar: [S; 2] = [S { x: 1, y: 2 }, S { x: 3, y: 4 }];
1115 let mut buf_ar = alloc::string::String::new();
1116 write!(&mut buf_ar, "{ar:#?}");
1117
1118 let av: SliceVec<S> = SliceVec::from(&mut ar);
1119 let mut buf_av = alloc::string::String::new();
1120 write!(&mut buf_av, "{av:#?}");
1121
1122 assert_eq!(buf_av, buf_ar)
1123 }
1124}