#![allow(unexpected_cfgs)]
#![cfg(not(doctest))]
pub trait ToNdarray1 {
type Out;
fn into_ndarray1(self) -> Self::Out;
}
pub trait ToNdarray2 {
type Out;
fn into_ndarray2(self) -> Self::Out;
}
pub trait ToNdarray3 {
type Out;
fn into_ndarray3(self) -> Self::Out;
}
pub trait RefNdarray1 {
type Out;
fn ref_ndarray1(self) -> Self::Out;
}
pub trait RefNdarray2 {
type Out;
fn ref_ndarray2(self) -> Self::Out;
}
pub trait RefNdarray3 {
type Out;
fn ref_ndarray3(self) -> Self::Out;
}
pub trait MutNdarray1 {
type Out;
fn mut_ndarray1(self) -> Self::Out;
}
pub trait MutNdarray2 {
type Out;
fn mut_ndarray2(self) -> Self::Out;
}
pub trait MutNdarray3 {
type Out;
fn mut_ndarray3(self) -> Self::Out;
}
pub trait ToNalgebra {
type Out;
fn into_nalgebra(self) -> Self::Out;
}
use core::convert::TryFrom;
use nalgebra::Dyn as Dy;
impl<'a, T> ToNalgebra for ndarray::ArrayView1<'a, T>
where
T: nalgebra::Scalar,
{
type Out = nalgebra::DVectorView<'a, T>;
fn into_nalgebra(self) -> Self::Out {
let len = Dy(self.len());
let ptr = self.as_ptr();
let stride: usize = TryFrom::try_from(self.strides()[0]).expect("Negative stride");
let storage = unsafe { nalgebra::ViewStorage::from_raw_parts(ptr, (len, nalgebra::Const::<1>), (nalgebra::Const::<1>, Dy(stride))) };
nalgebra::Matrix::from_data(storage)
}
}
#[allow(clippy::drop_non_drop)]
impl<'a, T> ToNalgebra for ndarray::ArrayViewMut1<'a, T>
where
T: nalgebra::Scalar,
{
type Out = nalgebra::DVectorViewMut<'a, T>;
fn into_nalgebra(mut self) -> Self::Out {
let len = Dy(self.len());
let stride: usize = TryFrom::try_from(self.strides()[0]).expect("Negative stride");
let ptr = self.as_mut_ptr();
let storage = unsafe {
drop(self);
nalgebra::ViewStorageMut::from_raw_parts(ptr, (len, nalgebra::Const::<1>), (nalgebra::Const::<1>, Dy(stride)))
};
nalgebra::Matrix::from_data(storage)
}
}
impl<T> ToNalgebra for ndarray::Array1<T>
where
T: nalgebra::Scalar,
{
type Out = nalgebra::DVector<T>;
fn into_nalgebra(self) -> Self::Out {
let len = Dy(self.len());
Self::Out::from_vec_generic(len, nalgebra::Const::<1>, self.into_raw_vec())
}
}
impl<'a, T> ToNalgebra for ndarray::ArrayView2<'a, T>
where
T: nalgebra::Scalar,
{
type Out = nalgebra::DMatrixView<'a, T, Dy, Dy>;
fn into_nalgebra(self) -> Self::Out {
let nrows = Dy(self.nrows());
let ncols = Dy(self.ncols());
let ptr = self.as_ptr();
let stride_row: usize = TryFrom::try_from(self.strides()[0]).expect("Negative row stride");
let stride_col: usize = TryFrom::try_from(self.strides()[1]).expect("Negative column stride");
let storage = unsafe { nalgebra::ViewStorage::from_raw_parts(ptr, (nrows, ncols), (Dy(stride_row), Dy(stride_col))) };
nalgebra::Matrix::from_data(storage)
}
}
#[allow(clippy::drop_non_drop)]
impl<'a, T> ToNalgebra for ndarray::ArrayViewMut2<'a, T>
where
T: nalgebra::Scalar,
{
type Out = nalgebra::DMatrixViewMut<'a, T, Dy, Dy>;
fn into_nalgebra(mut self) -> Self::Out {
let nrows = Dy(self.nrows());
let ncols = Dy(self.ncols());
let stride_row: usize = TryFrom::try_from(self.strides()[0]).expect("Negative row stride");
let stride_col: usize = TryFrom::try_from(self.strides()[1]).expect("Negative column stride");
let ptr = self.as_mut_ptr();
let storage = unsafe {
drop(self);
nalgebra::ViewStorageMut::from_raw_parts(ptr, (nrows, ncols), (Dy(stride_row), Dy(stride_col)))
};
nalgebra::Matrix::from_data(storage)
}
}
impl<T> ToNalgebra for ndarray::Array2<T>
where
T: nalgebra::Scalar,
{
type Out = nalgebra::DMatrix<T>;
fn into_nalgebra(self) -> Self::Out {
let std_layout = self.is_standard_layout();
let nrows = Dy(self.nrows());
let ncols = Dy(self.ncols());
let res = {
if std_layout {
let res = Self::Out::from_row_slice(self.nrows(), self.ncols(), self.as_slice().unwrap());
res
} else {
Self::Out::from_vec_generic(nrows, ncols, self.into_raw_vec())
}
};
res
}
}
use nalgebra::{
dimension::U1,
storage::{Storage, StorageMut},
Dim, Matrix, Scalar, Vector, ViewStorage, ViewStorageMut,
};
use ndarray::{ArrayView1, ArrayView2, ArrayViewMut1, ArrayViewMut2, ShapeBuilder};
impl<'a, N: Scalar, R: Dim, S> RefNdarray1 for &'a Vector<N, R, S>
where
S: Storage<N, R, U1>,
{
type Out = ArrayView1<'a, N>;
fn ref_ndarray1(self) -> Self::Out {
unsafe { ArrayView1::from_shape_ptr((self.shape().0,).strides((self.strides().0,)), self.as_ptr()) }
}
}
impl<'a, N: Scalar, R: Dim, S> MutNdarray1 for &'a mut Vector<N, R, S>
where
S: StorageMut<N, R, U1>,
{
type Out = ArrayViewMut1<'a, N>;
fn mut_ndarray1(self) -> Self::Out {
unsafe { ArrayViewMut1::from_shape_ptr((self.shape().0,).strides((self.strides().0,)), self.as_ptr().cast_mut()) }
}
}
impl<'a, N: Scalar, R: Dim, RStride: Dim, CStride: Dim> ToNdarray1 for Vector<N, R, ViewStorage<'a, N, R, U1, RStride, CStride>> {
type Out = ArrayView1<'a, N>;
fn into_ndarray1(self) -> Self::Out {
unsafe { ArrayView1::from_shape_ptr((self.shape().0,).strides((self.strides().0,)), self.as_ptr()) }
}
}
impl<'a, N: Scalar, R: Dim, RStride: Dim, CStride: Dim> ToNdarray1 for Matrix<N, R, U1, ViewStorageMut<'a, N, R, U1, RStride, CStride>> {
type Out = ArrayViewMut1<'a, N>;
fn into_ndarray1(self) -> Self::Out {
unsafe { ArrayViewMut1::from_shape_ptr((self.shape().0,).strides((self.strides().0,)), self.as_ptr().cast_mut()) }
}
}
impl<'a, N: Scalar, R: Dim, C: Dim, S> RefNdarray2 for &'a Matrix<N, R, C, S>
where
S: Storage<N, R, C>,
{
type Out = ArrayView2<'a, N>;
fn ref_ndarray2(self) -> Self::Out {
unsafe { ArrayView2::from_shape_ptr(self.shape().strides(self.strides()), self.as_ptr()) }
}
}
impl<'a, N: Scalar, R: Dim, C: Dim, S> MutNdarray2 for &'a mut Matrix<N, R, C, S>
where
S: StorageMut<N, R, C>,
{
type Out = ArrayViewMut2<'a, N>;
fn mut_ndarray2(self) -> Self::Out {
unsafe { ArrayViewMut2::from_shape_ptr(self.shape().strides(self.strides()), self.as_ptr().cast_mut()) }
}
}
impl<'a, N: Scalar, R: Dim, C: Dim, RStride: Dim, CStride: Dim> ToNdarray2 for Matrix<N, R, C, ViewStorage<'a, N, R, C, RStride, CStride>> {
type Out = ArrayView2<'a, N>;
fn into_ndarray2(self) -> Self::Out {
unsafe { ArrayView2::from_shape_ptr(self.shape().strides(self.strides()), self.as_ptr()) }
}
}
impl<'a, N: Scalar, R: Dim, C: Dim, RStride: Dim, CStride: Dim> ToNdarray2 for Matrix<N, R, C, ViewStorageMut<'a, N, R, C, RStride, CStride>> {
type Out = ArrayViewMut2<'a, N>;
fn into_ndarray2(self) -> Self::Out {
unsafe { ArrayViewMut2::from_shape_ptr(self.shape().strides(self.strides()), self.as_ptr().cast_mut()) }
}
}
#[cfg(feature = "nalgebra_std")]
mod std_impl {
use super::*;
use nalgebra::{allocator::Allocator, DVector, DefaultAllocator, Dynamic, VecStorage};
use ndarray::{Array1, Array2};
impl<'a, N: Scalar> ToNdarray1 for DVector<N> {
type Out = Array1<N>;
fn into_ndarray1(self) -> Self::Out {
Array1::from_shape_vec((self.shape().0,), self.data.into()).unwrap()
}
}
impl<'a, N: Scalar> ToNdarray2 for Matrix<N, Dynamic, Dynamic, VecStorage<N, Dynamic, Dynamic>>
where
DefaultAllocator: Allocator<N, Dynamic, Dynamic, Buffer = VecStorage<N, Dynamic, Dynamic>>,
{
type Out = Array2<N>;
fn into_ndarray2(self) -> Self::Out {
Array2::from_shape_vec(self.shape().strides(self.strides()), self.data.into()).unwrap()
}
}
}