1use core::borrow::{Borrow, BorrowMut};
2use core::cmp::Ordering;
3use core::fmt::{self, Debug};
4use core::hash::{Hash, Hasher};
5
6use typenum::{consts, Const};
7
8use super::{ArrayLength, ConstArrayLength, GenericArray, IntoArrayLength};
9
10use crate::functional::*;
11use crate::sequence::*;
12
13impl<T: Default, N: ArrayLength> Default for GenericArray<T, N> {
14 #[inline(always)]
15 fn default() -> Self {
16 Self::generate(|_| T::default())
17 }
18}
19
20impl<T: Clone, N: ArrayLength> Clone for GenericArray<T, N> {
21 #[inline]
22 fn clone(&self) -> GenericArray<T, N> {
23 self.map(Clone::clone)
24 }
25}
26
27impl<T: Copy, N: ArrayLength> Copy for GenericArray<T, N> where N::ArrayType<T>: Copy {}
28
29impl<T: PartialEq, N: ArrayLength> PartialEq for GenericArray<T, N> {
30 #[inline(always)]
31 fn eq(&self, other: &Self) -> bool {
32 **self == **other
33 }
34}
35impl<T: Eq, N: ArrayLength> Eq for GenericArray<T, N> {}
36
37impl<T: PartialOrd, N: ArrayLength> PartialOrd for GenericArray<T, N> {
38 #[inline(always)]
39 fn partial_cmp(&self, other: &GenericArray<T, N>) -> Option<Ordering> {
40 PartialOrd::partial_cmp(self.as_slice(), other.as_slice())
41 }
42}
43
44impl<T: Ord, N: ArrayLength> Ord for GenericArray<T, N> {
45 #[inline(always)]
46 fn cmp(&self, other: &GenericArray<T, N>) -> Ordering {
47 Ord::cmp(self.as_slice(), other.as_slice())
48 }
49}
50
51impl<T: Debug, N: ArrayLength> Debug for GenericArray<T, N> {
52 fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
53 self.as_slice().fmt(fmt)
54 }
55}
56
57impl<T, N: ArrayLength> Borrow<[T]> for GenericArray<T, N> {
58 #[inline(always)]
59 fn borrow(&self) -> &[T] {
60 self.as_slice()
61 }
62}
63
64impl<T, N: ArrayLength> BorrowMut<[T]> for GenericArray<T, N> {
65 #[inline(always)]
66 fn borrow_mut(&mut self) -> &mut [T] {
67 self.as_mut_slice()
68 }
69}
70
71impl<T, N: ArrayLength> AsRef<[T]> for GenericArray<T, N> {
72 #[inline(always)]
73 fn as_ref(&self) -> &[T] {
74 self.as_slice()
75 }
76}
77
78impl<T, N: ArrayLength> AsMut<[T]> for GenericArray<T, N> {
79 #[inline(always)]
80 fn as_mut(&mut self) -> &mut [T] {
81 self.as_mut_slice()
82 }
83}
84
85impl<T: Hash, N: ArrayLength> Hash for GenericArray<T, N> {
86 fn hash<H>(&self, state: &mut H)
87 where
88 H: Hasher,
89 {
90 Hash::hash(self.as_slice(), state)
91 }
92}
93
94impl<T, const N: usize> From<[T; N]> for GenericArray<T, ConstArrayLength<N>>
95where
96 Const<N>: IntoArrayLength,
97{
98 #[inline(always)]
99 fn from(value: [T; N]) -> Self {
100 GenericArray::from_array(value)
101 }
102}
103
104impl<T, const N: usize> From<GenericArray<T, ConstArrayLength<N>>> for [T; N]
105where
106 Const<N>: IntoArrayLength,
107{
108 #[inline(always)]
109 fn from(value: GenericArray<T, ConstArrayLength<N>>) -> Self {
110 value.into_array()
111 }
112}
113
114impl<'a, T, const N: usize> From<&'a [T; N]> for &'a GenericArray<T, ConstArrayLength<N>>
115where
116 Const<N>: IntoArrayLength,
117{
118 #[inline(always)]
119 fn from(slice: &'a [T; N]) -> Self {
120 unsafe { &*(slice.as_ptr() as *const GenericArray<T, ConstArrayLength<N>>) }
121 }
122}
123
124impl<'a, T, const N: usize> From<&'a mut [T; N]> for &'a mut GenericArray<T, ConstArrayLength<N>>
125where
126 Const<N>: IntoArrayLength,
127{
128 #[inline(always)]
129 fn from(slice: &'a mut [T; N]) -> Self {
130 unsafe { &mut *(slice.as_mut_ptr() as *mut GenericArray<T, ConstArrayLength<N>>) }
131 }
132}
133
134impl<T, const N: usize> AsRef<[T; N]> for GenericArray<T, ConstArrayLength<N>>
135where
136 Const<N>: IntoArrayLength,
137{
138 #[inline(always)]
139 fn as_ref(&self) -> &[T; N] {
140 unsafe { core::mem::transmute(self) }
141 }
142}
143impl<T, const N: usize> AsMut<[T; N]> for GenericArray<T, ConstArrayLength<N>>
144where
145 Const<N>: IntoArrayLength,
146{
147 #[inline(always)]
148 fn as_mut(&mut self) -> &mut [T; N] {
149 unsafe { core::mem::transmute(self) }
150 }
151}
152
153macro_rules! impl_tuple {
154 (@T $t:ident) => { T };
155
156 ($($len:ty => ($($t:ident,)*);)*) => {$(
157 impl<T> From<($(impl_tuple!(@T $t),)*)> for GenericArray<T, $len> {
158 #[inline]
159 #[allow(non_snake_case)]
160 fn from(tuple: ($(impl_tuple!(@T $t),)*)) -> Self {
161 let ($($t,)*) = tuple;
162 GenericArray::from_array([$($t,)*])
163 }
164 }
165
166 impl<T> From<GenericArray<T, $len>> for ($(impl_tuple!(@T $t),)*) {
167 #[inline]
168 #[allow(non_snake_case)]
169 fn from(array: GenericArray<T, $len>) -> Self {
170 let [$($t),*] = array.into_array();
171 ($($t,)*)
172 }
173 }
174 )*};
175}
176
177impl_tuple! {
178 consts::U1 => (A,);
179 consts::U2 => (A,B,);
180 consts::U3 => (A,B,C,);
181 consts::U4 => (A,B,C,D,);
182 consts::U5 => (A,B,C,D,E,);
183 consts::U6 => (A,B,C,D,E,F,);
184 consts::U7 => (A,B,C,D,E,F,G,);
185 consts::U8 => (A,B,C,D,E,F,G,H,);
186 consts::U9 => (A,B,C,D,E,F,G,H,I,);
187 consts::U10 => (A,B,C,D,E,F,G,H,I,J,);
188 consts::U11 => (A,B,C,D,E,F,G,H,I,J,K,);
189 consts::U12 => (A,B,C,D,E,F,G,H,I,J,K,L,);
190}
191
192#[cfg(test)]
193mod tests {
194 use crate::*;
195
196 #[test]
197 fn test_from_inference() {
198 let a = arr![1, 2, 3, 4];
199 let _: [i8; 4] = a.into();
200 }
201}