hicc_std/std_array.rs
1use hicc::{AbiClass, AbiType, ClassArray, ClassMutArray};
2use std::slice;
3
4hicc::cpp! {
5 #include <array>
6}
7
8hicc::import_class! {
9 #[cpp(class = "template<class T, size_t N> std::array<T, N>")]
10 pub class array<T> {
11 #[cpp(method = "const T* data() const")]
12 fn data(&self) -> *const T;
13 /// ```
14 /// use hicc_std::ArrayInt;
15 /// let array = ArrayInt::new_10();
16 /// assert_eq!(array.size(), 10);
17 /// ```
18 #[cpp(method = "size_t size() const")]
19 pub fn size(&self) -> usize;
20
21 /// ```
22 /// use hicc_std::ArrayInt;
23 /// let array = ArrayInt::new_10();
24 /// assert!(!array.is_empty());
25 /// ```
26 pub fn is_empty(&self) -> bool {
27 self.size() == 0
28 }
29
30 /// ```
31 /// use hicc_std::ArrayInt;
32 /// let mut array = ArrayInt::new_10();
33 /// assert_eq!(array.get(0), Some(&0));
34 /// assert_eq!(array.get(10), None);
35 /// ```
36 pub fn get(&self, pos: usize) -> Option<T::OutputRef<'_>> {
37 if pos < self.size() {
38 return unsafe { Some(self._at(pos)) };
39 }
40 None
41 }
42 #[cpp(method = "const T& at(size_t) const")]
43 unsafe fn _at(&self, pos: usize) -> &T;
44
45 /// ```
46 /// use hicc_std::ArrayInt;
47 /// let mut array = ArrayInt::new_10();
48 /// assert_eq!(array.get_mut(0), Some(&mut 0));
49 /// assert_eq!(array.get(10), None);
50 /// ```
51 pub fn get_mut(&mut self, pos: usize) -> Option<T::OutputRefMut<'_>> {
52 if pos < self.size() {
53 return unsafe { Some(self._at_mut(pos)) };
54 }
55 None
56 }
57 #[cpp(method = "T& at(size_t)")]
58 unsafe fn _at_mut(&mut self, pos: usize) -> &mut T;
59
60 /// ```
61 /// use hicc_std::ArrayInt;
62 /// let array = ArrayInt::new_10();
63 /// assert_eq!(array.back(), Some(&0));
64 /// ```
65 pub fn back(&self) -> Option<T::OutputRef<'_>> {
66 if !self.is_empty() {
67 return unsafe { Some(self._back()) };
68 }
69 None
70 }
71
72 #[cpp(method = "const T& back() const")]
73 unsafe fn _back(&self) -> &T;
74
75 /// ```
76 /// use hicc_std::ArrayInt;
77 /// let mut array = ArrayInt::new_10();
78 /// assert!(array.back_mut().is_some());
79 /// *array.back_mut().unwrap() += 1;
80 /// assert_eq!(array.back_mut(), Some(&mut 1));
81 /// ```
82 pub fn back_mut(&mut self) -> Option<T::OutputRefMut<'_>> {
83 if !self.is_empty() {
84 return unsafe { Some(self._back_mut()) };
85 }
86 None
87 }
88 #[cpp(method = "T& back()")]
89 unsafe fn _back_mut(&mut self) -> &mut T;
90
91 /// ```
92 /// use hicc_std::ArrayInt;
93 /// let array = ArrayInt::new_10();
94 /// assert!(array.front().is_some());
95 /// ```
96 pub fn front(&self) -> Option<T::OutputRef<'_>> {
97 if !self.is_empty() {
98 return unsafe { Some(self._front()) };
99 }
100 None
101 }
102 #[cpp(method = "const T& front() const")]
103 unsafe fn _front(&self) -> &T;
104
105 /// ```
106 /// use hicc_std::ArrayInt;
107 /// let mut array = ArrayInt::new_10();
108 /// assert!(array.front().is_some());
109 /// *array.front_mut().unwrap() += 1;
110 /// assert_eq!(array.front(), Some(&1));
111 /// ```
112 pub fn front_mut(&mut self) -> Option<T::OutputRefMut<'_>> {
113 if !self.is_empty() {
114 return unsafe { Some(self._front_mut()) };
115 }
116 None
117 }
118 #[cpp(method = "T& front()")]
119 unsafe fn _front_mut(&mut self) -> &mut T;
120
121 /// ```
122 /// use hicc_std::ArrayInt;
123 /// let mut array = ArrayInt::new_10();
124 /// array.fill(&1);
125 /// assert_eq!(array.front(), Some(&1));
126 /// ```
127 #[cpp(method = "void fill(const T&)")]
128 pub fn fill(&mut self, val: &T);
129 }
130}
131
132unsafe impl<T: AbiType + Sync> Send for array<T> {}
133unsafe impl<T: AbiType + Sync> Sync for array<T> {}
134
135impl<T: Sized + 'static> array<hicc::Pod<T>> {
136 /// ```
137 /// use hicc_std::ArrayInt;
138 /// let mut array = ArrayInt::new_10();
139 /// array.fill(&1);
140 /// array.as_slice().iter().for_each(|v| println!("{v}"));
141 /// ```
142 pub fn as_slice(&self) -> &[T] {
143 let data = self.data();
144 let size = self.size();
145 unsafe { slice::from_raw_parts(data, size) }
146 }
147
148 /// ```
149 /// use hicc_std::ArrayInt;
150 /// let mut array = ArrayInt::new_10();
151 /// array.fill(&1);
152 /// array.as_slice_mut().iter_mut().for_each(|v| {*v += 1;});
153 /// ```
154 pub fn as_slice_mut(&mut self) -> &mut [T] {
155 let data = self.data();
156 let size = self.size();
157 unsafe { slice::from_raw_parts_mut(data.cast_mut(), size) }
158 }
159}
160
161impl<T: AbiClass + 'static> array<T> {
162 /// ```
163 /// use hicc_std::{ArrayString, string};
164 /// let mut array = ArrayString::new_10();
165 /// array.fill(&string::from(c"hello"));
166 /// array.as_array().iter().for_each(|msg| {
167 /// // ...
168 /// println!("msg.size() = {}", msg.size());
169 /// });
170 /// ```
171 pub fn as_array(&self) -> ClassArray<'_, T> {
172 unsafe { self.data().into_array(self.size()) }
173 }
174
175 /// ```
176 /// use hicc_std::{ArrayString, string};
177 /// let mut array = ArrayString::new_10();
178 /// array.fill(&string::from(c"hello"));
179 /// array.as_mut_array().iter_mut().for_each(|mut msg| {
180 /// msg.append(1, b'c' as i8);
181 /// });
182 /// ```
183 pub fn as_mut_array(&mut self) -> ClassMutArray<'_, T> {
184 unsafe { self.data().into_mut_ptr().into_mut_array(self.size()) }
185 }
186}