-- | Provides the 'MMonoid' typeclass.
--
-- @since 0.1
module Numeric.Algebra.Multiplicative.MMonoid
  ( MMonoid (..),
  )
where

import Data.Complex (Complex)
import Data.Int (Int16, Int32, Int64, Int8)
import Data.Kind (Constraint, Type)
import Data.Ratio (Ratio)
import Data.Word (Word16, Word32, Word64, Word8)
import GHC.Natural (Natural)
import Numeric.Algebra.Multiplicative.MSemigroup (MSemigroup)

-- | Defines a monoid over a multiplicative semigroup.
--
-- @since 0.1
type MMonoid :: Type -> Constraint
class (MSemigroup m) => MMonoid m where
  -- | @since 0.1
  one :: m

-- | @since 0.1
instance MMonoid Double where
  one :: Double
one = Double
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Float where
  one :: Float
one = Float
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Int where
  one :: Int
one = Int
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Int8 where
  one :: Int8
one = Int8
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Int16 where
  one :: Int16
one = Int16
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Int32 where
  one :: Int32
one = Int32
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Int64 where
  one :: Int64
one = Int64
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Integer where
  one :: Integer
one = Integer
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Word where
  one :: Word
one = Word
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Word8 where
  one :: Word8
one = Word8
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Word16 where
  one :: Word16
one = Word16
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Word32 where
  one :: Word32
one = Word32
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Word64 where
  one :: Word64
one = Word64
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid Natural where
  one :: Natural
one = Natural
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid (Ratio Integer) where
  one :: Ratio Integer
one = Ratio Integer
1
  {-# INLINE one #-}

-- | @since 0.1
instance MMonoid (Ratio Natural) where
  one :: Ratio Natural
one = Ratio Natural
1
  {-# INLINE one #-}

-- | @since 0.1
instance (RealFloat a) => MMonoid (Complex a) where
  one :: Complex a
one = Complex a
1
  {-# INLINE one #-}