99use alloc:: vec;
1010#[ cfg( not( feature = "std" ) ) ]
1111use alloc:: vec:: Vec ;
12+ #[ allow( unused_imports) ]
13+ use std:: compile_error;
1214use std:: mem:: { forget, size_of} ;
1315use std:: ptr:: NonNull ;
1416
1517use crate :: imp_prelude:: * ;
1618use crate :: { dimension, ArcArray1 , ArcArray2 } ;
1719
18- /// Create an **[`Array`]** with one, two or
19- /// three dimensions.
20+ /// Create an **[`Array`]** with one, two, three, four, five, or six dimensions.
2021///
2122/// ```
2223/// use ndarray::array;
@@ -28,17 +29,49 @@ use crate::{dimension, ArcArray1, ArcArray2};
2829/// let a3 = array![[[1, 2], [3, 4]],
2930/// [[5, 6], [7, 8]]];
3031///
32+ /// let a4 = array![[[[1, 2, 3, 4]]]];
33+ ///
34+ /// let a5 = array![[[[[1, 2, 3, 4, 5]]]]];
35+ ///
36+ /// let a6 = array![[[[[[1, 2, 3, 4, 5, 6]]]]]];
37+ ///
3138/// assert_eq!(a1.shape(), &[4]);
3239/// assert_eq!(a2.shape(), &[2, 2]);
3340/// assert_eq!(a3.shape(), &[2, 2, 2]);
41+ /// assert_eq!(a4.shape(), &[1, 1, 1, 4]);
42+ /// assert_eq!(a5.shape(), &[1, 1, 1, 1, 5]);
43+ /// assert_eq!(a6.shape(), &[1, 1, 1, 1, 1, 6]);
3444/// ```
3545///
3646/// This macro uses `vec![]`, and has the same ownership semantics;
3747/// elements are moved into the resulting `Array`.
3848///
3949/// Use `array![...].into_shared()` to create an `ArcArray`.
50+ ///
51+ /// Attempts to crate 7D+ arrays with this macro will lead to
52+ /// a compiler error, since the difference between a 7D array
53+ /// of i32 and a 6D array of `[i32; 3]` is ambiguous. Higher-dim
54+ /// arrays can be created with [`ArrayD`].
55+ ///
56+ /// ```compile_fail
57+ /// use ndarray::array;
58+ /// let a7 = array![[[[[[[1, 2, 3]]]]]]];
59+ /// // error: Arrays of 7 dimensions or more (or ndarrays of Rust arrays) cannot be constructed with the array! macro.
60+ /// ```
4061#[ macro_export]
4162macro_rules! array {
63+ ( $( [ $( [ $( [ $( [ $( [ $( [ $( $x: expr) ,* $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ) => { {
64+ compile_error!( "Arrays of 7 dimensions or more (or ndarrays of Rust arrays) cannot be constructed with the array! macro." ) ;
65+ } } ;
66+ ( $( [ $( [ $( [ $( [ $( [ $( $x: expr) ,* $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ) => { {
67+ $crate:: Array6 :: from( vec![ $( [ $( [ $( [ $( [ $( [ $( $x, ) * ] , ) * ] , ) * ] , ) * ] , ) * ] , ) * ] )
68+ } } ;
69+ ( $( [ $( [ $( [ $( [ $( $x: expr) ,* $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ) => { {
70+ $crate:: Array5 :: from( vec![ $( [ $( [ $( [ $( [ $( $x, ) * ] , ) * ] , ) * ] , ) * ] , ) * ] )
71+ } } ;
72+ ( $( [ $( [ $( [ $( $x: expr) ,* $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ) => { {
73+ $crate:: Array4 :: from( vec![ $( [ $( [ $( [ $( $x, ) * ] , ) * ] , ) * ] , ) * ] )
74+ } } ;
4275 ( $( [ $( [ $( $x: expr) ,* $( , ) * ] ) ,+ $( , ) * ] ) ,+ $( , ) * ) => { {
4376 $crate:: Array3 :: from( vec![ $( [ $( [ $( $x, ) * ] , ) * ] , ) * ] )
4477 } } ;
@@ -233,63 +266,39 @@ pub fn arr2<A: Clone, const N: usize>(xs: &[[A; N]]) -> Array2<A>
233266 Array2 :: from ( xs. to_vec ( ) )
234267}
235268
236- impl < A , const N : usize > From < Vec < [ A ; N ] > > for Array2 < A >
237- {
238- /// Converts the `Vec` of arrays to an owned 2-D array.
239- ///
240- /// **Panics** if the product of non-zero axis lengths overflows `isize`.
241- fn from ( mut xs : Vec < [ A ; N ] > ) -> Self
242- {
243- let dim = Ix2 ( xs. len ( ) , N ) ;
244- let ptr = xs. as_mut_ptr ( ) ;
245- let cap = xs. capacity ( ) ;
246- let expand_len =
247- dimension:: size_of_shape_checked ( & dim) . expect ( "Product of non-zero axis lengths must not overflow isize." ) ;
248- forget ( xs) ;
249- unsafe {
250- let v = if size_of :: < A > ( ) == 0 {
251- Vec :: from_raw_parts ( ptr as * mut A , expand_len, expand_len)
252- } else if N == 0 {
253- Vec :: new ( )
254- } else {
255- // Guaranteed not to overflow in this case since A is non-ZST
256- // and Vec never allocates more than isize bytes.
257- let expand_cap = cap * N ;
258- Vec :: from_raw_parts ( ptr as * mut A , expand_len, expand_cap)
259- } ;
260- ArrayBase :: from_shape_vec_unchecked ( dim, v)
269+ macro_rules! impl_from_nested_vec {
270+ ( $arr_type: ty, $ix_type: tt, $( $n: ident) ,+) => {
271+ impl <A , $( const $n: usize ) ,+> From <Vec <$arr_type>> for Array <A , $ix_type>
272+ {
273+ fn from( mut xs: Vec <$arr_type>) -> Self
274+ {
275+ let dim = $ix_type( xs. len( ) , $( $n) ,+) ;
276+ let ptr = xs. as_mut_ptr( ) ;
277+ let cap = xs. capacity( ) ;
278+ let expand_len = dimension:: size_of_shape_checked( & dim)
279+ . expect( "Product of non-zero axis lengths must not overflow isize." ) ;
280+ forget( xs) ;
281+ unsafe {
282+ let v = if size_of:: <A >( ) == 0 {
283+ Vec :: from_raw_parts( ptr as * mut A , expand_len, expand_len)
284+ } else if $( $n == 0 ||) + false {
285+ Vec :: new( )
286+ } else {
287+ let expand_cap = cap $( * $n) +;
288+ Vec :: from_raw_parts( ptr as * mut A , expand_len, expand_cap)
289+ } ;
290+ ArrayBase :: from_shape_vec_unchecked( dim, v)
291+ }
292+ }
261293 }
262- }
294+ } ;
263295}
264296
265- impl < A , const N : usize , const M : usize > From < Vec < [ [ A ; M ] ; N ] > > for Array3 < A >
266- {
267- /// Converts the `Vec` of arrays to an owned 3-D array.
268- ///
269- /// **Panics** if the product of non-zero axis lengths overflows `isize`.
270- fn from ( mut xs : Vec < [ [ A ; M ] ; N ] > ) -> Self
271- {
272- let dim = Ix3 ( xs. len ( ) , N , M ) ;
273- let ptr = xs. as_mut_ptr ( ) ;
274- let cap = xs. capacity ( ) ;
275- let expand_len =
276- dimension:: size_of_shape_checked ( & dim) . expect ( "Product of non-zero axis lengths must not overflow isize." ) ;
277- forget ( xs) ;
278- unsafe {
279- let v = if size_of :: < A > ( ) == 0 {
280- Vec :: from_raw_parts ( ptr as * mut A , expand_len, expand_len)
281- } else if N == 0 || M == 0 {
282- Vec :: new ( )
283- } else {
284- // Guaranteed not to overflow in this case since A is non-ZST
285- // and Vec never allocates more than isize bytes.
286- let expand_cap = cap * N * M ;
287- Vec :: from_raw_parts ( ptr as * mut A , expand_len, expand_cap)
288- } ;
289- ArrayBase :: from_shape_vec_unchecked ( dim, v)
290- }
291- }
292- }
297+ impl_from_nested_vec ! ( [ A ; N ] , Ix2 , N ) ;
298+ impl_from_nested_vec ! ( [ [ A ; M ] ; N ] , Ix3 , N , M ) ;
299+ impl_from_nested_vec ! ( [ [ [ A ; L ] ; M ] ; N ] , Ix4 , N , M , L ) ;
300+ impl_from_nested_vec ! ( [ [ [ [ A ; K ] ; L ] ; M ] ; N ] , Ix5 , N , M , L , K ) ;
301+ impl_from_nested_vec ! ( [ [ [ [ [ A ; J ] ; K ] ; L ] ; M ] ; N ] , Ix6 , N , M , L , K , J ) ;
293302
294303/// Create a two-dimensional array with elements from `xs`.
295304///
0 commit comments