use ndarray::Dimension;
use crate::*;
impl< E, const ROWS : usize, const COLS : usize > IndexingRef
for Mat< ROWS, COLS, E, mat::DescriptorOrderColumnMajor >
where
E : MatEl,
E : nd::NdFloat,
{
#[ inline( always ) ]
fn lane_iter( &self, varying_dim : usize, lane : usize )
-> impl Iterator< Item = &Self::Scalar >
{
match varying_dim
{
0 => {
if COLS == 0
{
self
.raw_slice()
.iter()
.skip( 0 )
.step_by( 1 )
.take( 0 )
}
else
{
debug_assert!( lane < ROWS );
self
.raw_slice()
.iter()
.skip( lane )
.step_by( ROWS )
.take( COLS )
}
},
1 => {
if ROWS == 0
{
self
.raw_slice()
.iter()
.skip( 0 )
.step_by( 1 )
.take( 0 )
}
else
{
debug_assert!( lane < COLS, "lane:{lane} | COLS:{COLS}" );
self
.raw_slice()
.iter()
.skip( lane * ROWS )
.step_by( 1 )
.take( ROWS )
}
},
_ => panic!( "Invalid dimension: {}", varying_dim ),
}
}
#[ inline( always ) ]
fn lane_indexed_iter( &self, varying_dim : usize, lane : usize ) -> impl Iterator< Item = ( <Self as Indexable>::Index, &Self::Scalar ) >
{
self.lane_iter( varying_dim, lane ).enumerate().map( move | ( i, value ) |
{
match varying_dim
{
0 => ( Ix2( lane, i ), value ), 1 => ( Ix2( i, lane ), value ), _ => panic!( "Invalid dimension: {}", varying_dim ),
}
})
}
#[ inline ]
fn iter_unstable( &self ) -> impl Iterator< Item = &Self::Scalar >
{
self.raw_slice().iter()
}
#[ inline ]
fn iter_indexed_unstable( &self ) -> impl Iterator< Item = ( <Self as Indexable>::Index, &Self::Scalar ) >
{
self.iter_unstable().enumerate().map( | ( i, value ) |
{
let row = i % ROWS;
let col = i / ROWS;
( Ix2( row, col ), value )
})
}
#[ inline ]
fn iter_lsfirst( &self ) -> impl Iterator< Item = &Self::Scalar >
{
( 0..ROWS ).flat_map( move | row |
{
self.raw_slice()
.iter()
.skip( row )
.step_by( ROWS )
.take( COLS )
})
}
#[ inline ]
fn iter_indexed_lsfirst( &self ) -> impl Iterator< Item = ( <Self as Indexable>::Index, &Self::Scalar ) >
{
self.iter_lsfirst().enumerate().map( | ( i, value ) |
{
let row = i / COLS;
let col = i % COLS;
( Ix2( row, col ), value )
})
}
#[ inline ]
fn iter_msfirst( &self ) -> impl Iterator< Item = &Self::Scalar >
{
self.raw_slice().iter()
}
#[ inline ]
fn iter_indexed_msfirst( &self ) -> impl Iterator< Item = ( <Self as Indexable>::Index, &Self::Scalar ) >
{
self.iter_msfirst().enumerate().map( | ( i, value ) |
{
let row = i % ROWS;
let col = i / ROWS;
( Ix2( row, col ), value )
})
}
}
impl< E, const ROWS : usize, const COLS : usize > IndexingMut
for Mat< ROWS, COLS, E, mat::DescriptorOrderColumnMajor >
where
E : MatEl,
E : nd::NdFloat,
{
fn lane_iter_mut( &mut self, varying_dim : usize, lane : usize ) -> impl Iterator< Item = &mut Self::Scalar >
{
match varying_dim
{
0 =>
{
if COLS == 0
{
self
.raw_slice_mut()
.iter_mut()
.skip( 0 )
.step_by( 1 )
.take( 0 )
}
else
{
debug_assert!( lane < ROWS );
self
.raw_slice_mut()
.iter_mut()
.skip( lane )
.step_by( ROWS )
.take( COLS )
}
},
1 =>
{
if ROWS == 0
{
self
.raw_slice_mut()
.iter_mut()
.skip( 0 )
.step_by( 1 )
.take( 0 )
}
else
{
debug_assert!( lane < COLS, "lane:{lane} | COLS:{COLS}" );
self
.raw_slice_mut()
.iter_mut()
.skip( lane * ROWS )
.step_by( 1 )
.take( ROWS )
}
},
_ => panic!( "Invalid dimension: {}", varying_dim ),
}
}
fn lane_iter_indexed_mut( &mut self, varying_dim : usize, lane : usize ) -> impl Iterator< Item = ( <Self as Indexable>::Index, &mut Self::Scalar ) >
{
self.lane_iter_mut( varying_dim, lane ).enumerate().map( move | ( i, value ) |
{
match varying_dim
{
0 => ( Ix2( lane, i ), value ), 1 => ( Ix2( i, lane ), value ), _ => panic!( "Invalid dimension: {}", varying_dim ),
}
})
}
fn iter_unstable_mut( &mut self ) -> impl Iterator< Item = &mut Self::Scalar >
{
self.raw_slice_mut().iter_mut()
}
fn iter_indexed_unstable_mut( &mut self ) -> impl Iterator< Item = ( <Self as Indexable>::Index, &mut Self::Scalar ) >
{
self.iter_unstable_mut().enumerate().map( | ( i, value ) |
{
let row = i % ROWS;
let col = i / ROWS;
( Ix2( row, col ), value )
})
}
fn iter_lsfirst_mut( &mut self ) -> impl Iterator< Item = &mut Self::Scalar >
{
let ptr = self.raw_slice_mut().as_mut_ptr();
( 0..ROWS ).flat_map( move | row |
{
( 0..COLS).map( move | col |
{
#[ allow( unsafe_code ) ]
unsafe { &mut *ptr.add( col * ROWS + row ) }
})
})
}
fn iter_indexed_lsfirst_mut( &mut self ) -> impl Iterator< Item = ( <Self as Indexable>::Index, &mut Self::Scalar ) >
{
self.iter_lsfirst_mut().enumerate().map( | ( i, value ) |
{
let row = i / COLS;
let col = i % COLS;
( Ix2( row, col ), value )
})
}
fn iter_msfirst_mut( &mut self ) -> impl Iterator< Item = &mut Self::Scalar >
{
self.raw_slice_mut().iter_mut()
}
fn iter_indexed_msfirst_mut( &mut self ) -> impl Iterator< Item = ( < Self as Indexable >::Index, &mut Self::Scalar ) >
{
self.iter_msfirst_mut().enumerate().map( | ( i, value ) |
{
let row = i % ROWS;
let col = i / ROWS;
( Ix2( row, col ), value )
})
}
}
impl< E, const ROWS : usize, const COLS : usize > ConstLayout
for Mat< ROWS, COLS, E, mat::DescriptorOrderColumnMajor >
where
E : MatEl,
{
#[ inline( always ) ]
fn scalar_offset( index : <Self as Indexable>::Index ) -> usize
{
use mdmath_core::plain::DimOffset;
let ( row, col ) = index.into_pattern();
[ COLS, ROWS ].offset( &Ix2( col, row ) )
}
}
impl< E, const ROWS : usize, const COLS : usize, > RawSliceMut
for Mat< ROWS, COLS, E, mat::DescriptorOrderColumnMajor >
where
E : MatEl,
Self : Collection< Scalar = E >,
{
#[ inline( always ) ]
fn raw_slice_mut( &mut self ) -> &mut [ Self::Scalar ]
{
#[ allow( unsafe_code ) ]
unsafe { std::slice::from_raw_parts_mut( self.as_mut_ptr() as *mut Self::Scalar, ROWS * COLS ) }
}
#[ inline( always ) ]
fn raw_set_slice( &mut self, scalars : &[ Self::Scalar ] )
{
self.raw_slice_mut().copy_from_slice( scalars );
}
#[ inline( always ) ]
fn raw_set< const N : usize >( mut self, scalars : [ Self::Scalar ; N ] ) -> Self
{
debug_assert_eq!( scalars.len(), ROWS*COLS, "Size should be equal" );
self.raw_slice_mut().copy_from_slice( &scalars );
self
}
#[ inline( always ) ]
fn with_row_major( mut self, scalars : &[ Self::Scalar ] ) -> Self {
debug_assert_eq!( scalars.len(), ROWS*COLS, "Size should be equal" );
let ptr = scalars.as_ptr();
let scalars : Vec< Self::Scalar > =
( 0..COLS ).flat_map( move | col |
{
( 0..ROWS ).map( move | row |
{
#[ allow( unsafe_code ) ]
unsafe { *ptr.add( row * COLS + col ) }
})
})
.collect();
self.raw_set_slice( scalars.as_ref() );
self
}
fn with_column_major( mut self, scalars : &[ Self::Scalar ] ) -> Self {
self.raw_set_slice( scalars );
self
}
}