module Data.Semigroup.Act where
import Data.Semigroup
import qualified Numeric.Natural.Internal as NI
class Semigroup g => SemigroupAct g a where
act :: g -> (a -> a)
class (Monoid g, SemigroupAct g a) => MonoidAct g a where
newtype OptionSet g a = OptionSet { getOptionSet :: a }
instance (SemigroupAct g a, Semigroup g)
=> SemigroupAct (Option g) (OptionSet g a) where
act (Option Nothing) x = x
act (Option (Just g)) (OptionSet x) = OptionSet $ (act g) x
instance (SemigroupAct g a, Monoid g)
=> MonoidAct (Option g) (OptionSet g a) where
newtype SelfAct a = SelfAct a
deriving (Show, Read, Eq, Ord)
instance Functor SelfAct where
fmap f (SelfAct x) = SelfAct (f x)
instance Semigroup g => Semigroup (SelfAct g) where
(SelfAct x) <> (SelfAct y) = SelfAct $ x <> y
instance (Monoid g) => Monoid (SelfAct g) where
mempty = SelfAct mempty
mappend (SelfAct x) (SelfAct y) = SelfAct $ x `mappend` y
instance Semigroup g => SemigroupAct (SelfAct g) (SelfAct g) where
act = (<>)
instance (Semigroup g, Monoid g) => MonoidAct (SelfAct g) (SelfAct g) where
newtype Repeat a = Repeat { unwrapRepeat :: a }
deriving (Show, Read, Eq, Ord)
instance Functor Repeat where
fmap f (Repeat x) = Repeat (f x)
instance (Monoid w, NI.Whole n) => SemigroupAct (Product n) (Repeat w) where
act (Product m) (Repeat x)
| m == 0 = Repeat mempty
| otherwise = Repeat . unwrapMonoid $ times1p (NI.unsafePred m) (WrapMonoid x)