Documentation
use std::ops::Add;

use crate::arr::{core::plain_index, shape_iterator::ShapeIterator, vec::core::ArrVec};

impl<T> From<&Vec<T>> for ArrVec<T>
where
    T: Default + Add + Copy,
{
    fn from(value: &Vec<T>) -> Self {
        ArrVec {
            buff: value.clone(),
            shape: vec![value.len()],
        }
    }
}

impl<T> From<Vec<T>> for ArrVec<T>
where
    T: Default + Add + Copy,
{
    fn from(value: Vec<T>) -> Self {
        Self::from(&value)
    }
}

impl<const C: usize, const F: usize, T> From<[[T; C]; F]> for ArrVec<T>
where
    T: Default + Add + Copy,
{
    fn from(value: [[T; C]; F]) -> Self {
        let mut buff = vec![T::default(); C * value.len()];
        let shape = vec![value.len(), C];
        for index in ShapeIterator::new(&shape) {
            let plain = plain_index(&shape, &shape, &index);
            buff[plain] = value[index[0]][index[1]];
        }
        ArrVec { buff, shape }
    }
}

impl<T> From<&[T]> for ArrVec<T>
where
    T: Default + Add + Copy,
{
    fn from(value: &[T]) -> Self {
        Self::from(Vec::from(value))
    }
}

impl<T, const N: usize> From<&[T; N]> for ArrVec<T>
where
    T: Default + Add + Copy,
{
    fn from(value: &[T; N]) -> Self {
        Self::from(Vec::from(value))
    }
}

impl<T, const N: usize> From<[T; N]> for ArrVec<T>
where
    T: Default + Add + Copy,
{
    fn from(value: [T; N]) -> Self {
        Self::from(Vec::from(value))
    }
}