//! Abstraction of ring structure\
use core::ops::{Mul, Add};
use crate::group::AbelianGroup;
pub mod modring;
/// (R, add, mul) is a ring if
///
/// 1. (R, add) is an abelian group
/// 2. R is closed under multiplication
/// 3. multiplication in R is associative
/// 4. multiplication is distributed over addition
pub trait Ring:
Sized +
AbelianGroup + // 1
Mul<Output = Self> + // 2
AssociativeMul + // 3
DistributiveMul // 4
{ }
/// # Safety
///
/// this trait is safe only when for all a, b, c: a * (b * c) = (a * b) * c
pub trait AssociativeMul: Sized + Mul<Output = Self> {}
/// # Safety
///
/// this trait is safe only when for all a, b, c: a * (b + c) = a * b + a * c
pub trait DistributiveMul: Sized + Mul<Output = Self> + Add<Output = Self> {}