use crate::mapping::{DenseMapping, FlatMapping, GeneralMapping, Mapping, StridedMapping};
use crate::shape::Shape;
pub trait Layout {
type NonUniform: Layout;
type NonUnitStrided: Layout;
type Uniform: Uniform;
type UnitStrided: UnitStrided;
type Merge<L: Layout>: Layout;
type Mapping<S: Shape>: Mapping<Shape = S, Layout = Self>;
const IS_UNIFORM: bool;
const IS_UNIT_STRIDED: bool;
}
pub trait Uniform: Layout<Uniform = Self, UnitStrided = Dense, NonUnitStrided = Flat> {}
pub trait UnitStrided: Layout<Uniform = Dense, UnitStrided = Self, NonUniform = General> {}
pub struct Dense;
pub struct Flat;
pub struct General;
pub struct Strided;
impl Layout for Dense {
type NonUniform = General;
type NonUnitStrided = Flat;
type Uniform = Self;
type UnitStrided = Self;
type Merge<L: Layout> = L;
type Mapping<S: Shape> = DenseMapping<S>;
const IS_UNIFORM: bool = true;
const IS_UNIT_STRIDED: bool = true;
}
impl Layout for Flat {
type NonUniform = Strided;
type NonUnitStrided = Self;
type Uniform = Self;
type UnitStrided = Dense;
type Merge<L: Layout> = L::NonUnitStrided;
type Mapping<S: Shape> = FlatMapping<S>;
const IS_UNIFORM: bool = true;
const IS_UNIT_STRIDED: bool = false;
}
impl Layout for General {
type NonUniform = Self;
type NonUnitStrided = Strided;
type Uniform = Dense;
type UnitStrided = Self;
type Merge<L: Layout> = L::NonUniform;
type Mapping<S: Shape> = GeneralMapping<S>;
const IS_UNIFORM: bool = false;
const IS_UNIT_STRIDED: bool = true;
}
impl Layout for Strided {
type NonUniform = Self;
type NonUnitStrided = Self;
type Uniform = Flat;
type UnitStrided = General;
type Merge<L: Layout> = Self;
type Mapping<S: Shape> = StridedMapping<S>;
const IS_UNIFORM: bool = false;
const IS_UNIT_STRIDED: bool = false;
}
impl Uniform for Dense {}
impl Uniform for Flat {}
impl UnitStrided for Dense {}
impl UnitStrided for General {}