flexiwrap-0.1.0: Data/Flex/Wrap.hs
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE Rank2Types #-}
{-# LANGUAGE EmptyDataDecls #-}
{-# LANGUAGE TypeSynonymInstances #-}
{-# LANGUAGE MultiParamTypeClasses, FunctionalDependencies #-}
{-# LANGUAGE UndecidableInstances #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE OverlappingInstances #-}
-- .$Header: c:/Source/Haskell/Wrapper/Data/Flex/RCS/Wrap.hs,v 1.18 2011/09/20 23:46:14 dosuser Exp dosuser $
-- | The flexible value wrapper @'FlexiWrap'@ and associated types and classes
module Data.Flex.Wrap (
-- * @'FlexiWrap'@
-- | and related instance machinery
-- ** @'FlexiWrap'@
-- | with a type synonym and alternative constructors
FlexiWrap(..),
FW,
flexiWrap,
flexiWrapP,
-- ** Instance selectors
FWDefaultEq(..),
FWTransparentEq(..),
FWDefaultOrd(..),
FWTransparentOrd(..),
FWReverseOrd(..),
FWDefaultShowRead(..),
FWLiteralShowRead(..),
FWTransparentShowRead(..),
FWDefaultArbitrary(..),
FWTransparentArbitrary(..),
FWDefaultMonoid(..),
FWTransparentMonoid(..),
FWDualMonoid(..),
FWEndoMonoid(..),
FWAllMonoid(..),
FWAnyMonoid(..),
FWSumMonoid(..),
FWProductMonoid(..),
FWFirstMonoid(..),
FWLastMonoid(..),
-- ** Machinery for @'Eq'@ instances
FWEq,
FWEquals(..),
FWNotEquals(..),
-- ** Machinery for @'Ord'@ instances
FWOrd,
FWCompare(..),
-- ** Machinery for @'Show'@ and @'Read'@ instances
FWShowRead,
FWShow(..),
FWRead(..),
-- ** Machinery for @'Arbitrary'@ instances
FWArbitraryC,
FWArbitrary(..),
FWCoarbitrary(..),
-- ** Machinery for @'Monoid'@ instances
FWMonoid,
FWMempty(..),
FWMappend(..),
-- ** Utility functions
inFlexiWrap,
inFlexiWrap2,
-- * Experimental features
FWNormAppend,
FWrap(..),
FWIsWrapped,
FWAlreadyWrapped(..),
FWNewWrapper(..)
) where
import Control.Applicative (Applicative(..))
-- , (<$>), liftA2, Alternative(..))
import Data.Foldable as F (Foldable(..))
import Data.Monoid (Monoid(..))
import qualified Data.Traversable as T (Traversable(..))
import Test.QuickCheck (Arbitrary(..), Gen)
import Data.Type.Apply (Apply(..))
import Data.Type.Eq (TypeCast)
import Data.Type.Proxy (Proxy(..))
import Data.Type.TList ((:*:), TNil)
import Data.Flex.Arbitrary (WrapCoarbitrary(..))
import Data.Flex.Utils (inCompose, inCompose2, on)
-- begin FlexiWrap
-- | The flexible value wrapper
newtype FlexiWrap s a = FlexiWrap {unFlexiWrap :: a}
-- | A handy abbreviated type synonym
type FW = FlexiWrap
-- | An alternative constructor
flexiWrap :: s -> a -> FW s a
flexiWrap _ = FlexiWrap
-- | An alternative constructor using a proxy
flexiWrapP :: Proxy s -> a -> FW s a
flexiWrapP _ = FlexiWrap
-- | The implementation of fmap for @'Functor' ('FW' s)@
inFlexiWrap :: (a -> b) -> (FW s a -> FW s b)
inFlexiWrap = inCompose unFlexiWrap FlexiWrap
-- | An extension of fmap to two-argument functions
inFlexiWrap2 :: (a -> b -> c) -> (FW s a -> FW s b -> FW s c)
-- inFlexiWrap2 = inCompose unFlexiWrap $ inCompose unFlexiWrap FlexiWrap
inFlexiWrap2 = inCompose2 unFlexiWrap FlexiWrap
-- TODO: Use flexible instance machinery?
instance Functor (FW t) where
fmap = inFlexiWrap
instance Applicative (FW t) where
pure = FlexiWrap
(<*>) = inFlexiWrap . unFlexiWrap
instance F.Foldable (FW t) where
foldr f z (FlexiWrap a) = f a z
instance T.Traversable (FW t) where
traverse = (fmap FlexiWrap .) . (. unFlexiWrap)
sequenceA = fmap FlexiWrap . unFlexiWrap
instance Monad (FW t) where
return = FlexiWrap
(>>=) = flip (. unFlexiWrap)
-- | Utility class to append two type-level lists
--
-- append \<s> and \<t> to produce \<u>.
-- \<s> may or may not be terminated by @'TNil'@;
-- if so, it does not appear in the result
class FWNormAppend s t u | s t -> u
instance FWNormAppend TNil t t
instance FWNormAppend s t u => FWNormAppend (x :*: s) t (x :*: u)
instance TypeCast u (x :*: t) => FWNormAppend x t u
-- | Utility class to create or tag-extend a wrapper
-- class FWrap w a b where
class FWrap w a b | w a -> b where
fWrap :: w -> a -> b
-- | Analysis class to determine whether an argument is already wrapped,
-- used for @'FWrap'@
class FWIsWrapped a r | a -> r
-- | Result type for @'FWIsWrapped'@
data FWAlreadyWrapped = FWAlreadyWrapped
-- | Result type for @'FWIsWrapped'@
data FWNewWrapper = FWNewWrapper
-- | Function identifier type for @'Apply'@
data FWFWrap s a = FWFWrap
instance FWIsWrapped (FW s a) FWAlreadyWrapped
instance TypeCast r FWNewWrapper => FWIsWrapped a r
-- | * Implementation instance for @'FWrap'@
instance Apply (FWFWrap u a) FWNewWrapper (a -> FW u a) where
apply _ _ = FlexiWrap
-- | * Implementation instance for @'FWrap'@
instance Apply (FWFWrap u (FW s a)) FWAlreadyWrapped (FW s a -> FW u a) where
apply _ _ = FlexiWrap . unFlexiWrap
-- | Function identifier type for @'Apply'@
data FWTag
-- | * Analysis instance for @'FWTag'@
instance Apply FWTag (FW t a) t
-- | * Analysis instance for @'FWTag'@
instance TypeCast r TNil => Apply FWTag a r
-- | * Coordinating instance definition for @'FWrap'@
instance forall a b s t u w. (
Apply FWTag a t,
FWNormAppend s t u,
FWIsWrapped a w,
Apply (FWFWrap u a) w (a -> FW u b)
) =>
FWrap s a (FW u b)
where
fWrap _ = apply (undefined :: FWFWrap u a) (undefined :: w)
{-
instance FWNormAppend s t u => FWrap s (FW t a) (FW u a) where
fWrap _ (FlexiWrap a) = FlexiWrap a
instance FWNormAppend s TNil u => FWrap s a (FW u a) where
fWrap _ = FlexiWrap
-}
{-
instance FWrap TNil (FW s a) (FW s a) where
fWrap _ = id
instance FWrap s (FW t a) (FW u a) =>
FWrap (w :*: s) (FW t a) (FW (w :*: u) a) where
fWrap _ (FlexiWrap a) = FlexiWrap a
instance TypeCast t (w :*: s) => FWrap w (FW s a) (FW t a) where
fWrap _ (FlexiWrap a) = FlexiWrap a
{-
instance FWrap w (FW s a) (FW (w :*: s) a) where
fWrap _ (FlexiWrap a) = FlexiWrap a
-}
{-
instance TypeCast r (FW TNil a) => FWrap TNil a r where
fWrap _ = FlexiWrap
-}
instance FWrap TNil a (FW TNil a) where
fWrap _ = FlexiWrap
instance FWrap s a (FW t a) => FWrap (x :*: s) a (FW (x :*: t) a) where
fWrap _ = FlexiWrap
instance FWrap w a (FW (w :*: TNil) a) where
fWrap _ = FlexiWrap
-}
-- TODO: FWDefaultAll (except Num) selector
-- Eq
-- | Analysis class for @'Eq'@ instance selection.
-- You need a specific instance of this for any instance selectors
-- you may define.
class FWEq a r | a -> r
-- | Instance selector type for the default
-- (transparent) implementation of @'Eq'@
data FWDefaultEq = FWDefaultEq
-- | Instance selector type for the (default)
-- transparent implementation of @'Eq'@
data FWTransparentEq = FWTransparentEq
-- | Function identifier type for @'Apply'@.
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWEquals t a = FWEquals
-- | Function identifier type for @'Apply'@
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWNotEquals t a = FWNotEquals
-- | * Default instance
instance TypeCast r FWTransparentEq => FWEq (FW t a) r
-- | * Propagated instance
instance FWEq (FW s a) r => FWEq (FW (x :*: s) a) r
-- | * Specific @'FWDefaultEq'@ instance
instance FWShowRead (FW (FWDefaultEq :*: s) a) FWTransparentEq
-- | * Specific @'FWTransparentEq'@ instance
instance FWShowRead (FW (FWTransparentEq :*: s) a) FWTransparentEq
-- | * Implementation instance for @'Eq'@ instance selection
instance Eq a => Apply (FWEquals t a) FWTransparentEq
(FW t a -> FW t a -> Bool)
where
apply _ _ = (==) `on` unFlexiWrap
-- | * Implementation instance for @'Eq'@ instance selection
instance Eq a => Apply (FWNotEquals t a) FWTransparentEq
(FW t a -> FW t a -> Bool)
where
apply _ _ = (/=) `on` unFlexiWrap
-- | * Coordinating instance for @'Eq'@
instance forall t a r. (Apply (FWEquals t a) r (FW t a -> FW t a -> Bool),
Apply (FWNotEquals t a) r (FW t a -> FW t a -> Bool),
FWEq (FW t a) r
) =>
Eq (FW t a) where
(==) = apply (undefined :: FWEquals t a) (undefined :: r)
(/=) = apply (undefined :: FWNotEquals t a) (undefined :: r)
-- Ord
-- | Analysis class for @'Ord'@ instance selection
-- You need a specific instance of this for any instance selectors
-- you may define.
class FWOrd a r | a -> r
-- | Instance selector type for the default (transparent) @'Ord'@ instance
data FWDefaultOrd = FWDefaultOrd
-- | Instance selector type for the (default) transparent @'Ord'@ instance
data FWTransparentOrd = FWTransparentOrd
-- | Instance selector type for a reversed @'Ord'@ instance
data FWReverseOrd = FWReverseOrd
-- | Function identifier type for @'Apply'@.
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWCompare t a = FWCompare
-- | * Default instance
instance TypeCast r FWTransparentOrd => FWOrd (FW t a) r
-- | * Propagated instance
instance FWOrd (FW s a) r => FWOrd (FW (x :*: s) a) r
-- | * Specific @'FWDefaultOrd'@ instance
instance FWOrd (FW (FWDefaultOrd :*: s) a) FWTransparentOrd
-- | * Specific @'FWTransparentOrd'@ instance
instance FWOrd (FW (FWTransparentOrd :*: s) a) FWTransparentOrd
-- | * Specific @'FWReverseOrd'@ instance
instance FWOrd (FW (FWReverseOrd :*: s) a) FWReverseOrd
-- | ** Implementation instance for @'Ord'@ instance selection
instance Ord a => Apply (Proxy (FWCompare t a)) (Proxy FWTransparentOrd)
(FW t a -> FW t a -> Ordering)
where
apply _ _ = compare `on` unFlexiWrap
-- | ** Implementation instance for @'Ord'@ instance selection
instance Ord a => Apply (Proxy (FWCompare t a)) (Proxy FWReverseOrd)
(FW t a -> FW t a -> Ordering)
where
apply _ _ = flip compare `on` unFlexiWrap
-- | * Coordinating instance of @'Ord'@
instance forall t a r. (
Apply (Proxy (FWCompare t a)) (Proxy r)
(FW t a -> FW t a -> Ordering),
FWOrd (FW t a) r,
Eq (FW t a)
) =>
Ord (FW t a) where
compare = apply (Proxy :: Proxy (FWCompare t a)) (Proxy :: Proxy r)
-- Show/Read
app_prec :: Int
app_prec = 10
-- | Analysis class for @'Show/Read'@ instance selection
-- You need a specific instance of this for any instance selectors
-- you may define.
class FWShowRead a r | a -> r
-- | Instance selector type for the default (literal) @'Show'/'Read'@
-- instances
data FWDefaultShowRead = FWDefaultShowRead deriving (Show, Read)
-- | Instance selector type for the (default) literal @'Show'/'Read'@
-- instances
data FWLiteralShowRead = FWLiteralShowRead deriving (Show, Read)
-- | Instance selector type for transparent @'Show'/'Read'@ instances
data FWTransparentShowRead = FWTransparentShowRead deriving (Show, Read)
-- | Function identifier type for @'Apply'@.
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWShow t a = FWShow
-- | Function identifier type for @'Apply'@.
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWRead t a = FWRead
-- | * Default instance
instance TypeCast r FWLiteralShowRead => FWShowRead (FW t a) r
-- | * Propagated instance
instance FWShowRead (FW s a) r => FWShowRead (FW (x :*: s) a) r
-- | * Specific @'FWDefaultShowRead'@ instance
instance FWShowRead (FW (FWDefaultShowRead :*: s) a) FWLiteralShowRead
-- | * Specific @'FWLiteralShowRead'@ instance
instance FWShowRead (FW (FWLiteralShowRead :*: s) a) FWLiteralShowRead
-- | * Specific @'FWTransparentShowRead'@ instance
instance FWShowRead (FW (FWTransparentShowRead :*: s) a) FWTransparentShowRead
-- | ** Implementation instance for @'Show'@ instance selection
instance Show a =>
Apply (Proxy (FWShow t a)) (Proxy FWLiteralShowRead)
(Int -> FW t a -> ShowS)
where
apply _ _ d (FlexiWrap w) = showParen (d > app_prec) $
showString "FlexiWrap " . showsPrec (app_prec+1) w
-- | ** Implementation instance for @'Read'@ instance selection
instance Read a =>
Apply (Proxy (FWRead t a)) (Proxy FWLiteralShowRead)
(Int -> ReadS (FW t a))
where
apply _ _ d r = readParen
(d > app_prec)
(\v -> [(FlexiWrap m, t) |
("FlexiWrap", s) <- lex v,
(m, t) <- readsPrec (app_prec+1) s
])
r
-- | ** Implementation instance for @'Show'@ instance selection
instance Show a =>
Apply (Proxy (FWShow t a)) (Proxy FWTransparentShowRead)
(Int -> FW t a -> ShowS)
where
apply _ _ d (FlexiWrap w) = showParen (d > app_prec) $
showsPrec (app_prec+1) w
-- | ** Implementation instance for @'Read'@ instance selection
instance Read a =>
Apply (Proxy (FWRead t a)) (Proxy FWTransparentShowRead)
(Int -> ReadS (FW t a))
where
apply _ _ d r = readParen
(d > app_prec)
(\s -> [(FlexiWrap m, t) |
(m, t) <- readsPrec (app_prec+1) s
])
r
-- | * Coordinating instance of @'Show'@
instance forall t a r. (
Apply (Proxy (FWShow t a)) (Proxy r)
(Int -> FW t a -> ShowS),
FWShowRead (FW t a) r
) =>
Show (FW t a) where
showsPrec = apply (Proxy :: Proxy (FWShow t a)) (Proxy :: Proxy r)
-- | * Coordinating instance of @'Read'@
instance forall t a r. (
Apply (Proxy (FWRead t a)) (Proxy r)
(Int -> ReadS (FW t a)),
FWShowRead (FW t a) r
) =>
Read (FW t a) where
readsPrec = apply (Proxy :: Proxy (FWRead t a)) (Proxy :: Proxy r)
-- Arbitrary
-- | Analysis class for @'Arbitrary'@ instance selection
-- You need a specific instance of this for any instance selectors
-- you may define.
class FWArbitraryC a r | a -> r
-- | Instance selector type for the default (transparent) @'Arbitrary'@
-- instances
data FWDefaultArbitrary = FWDefaultArbitrary deriving (Show, Read)
-- | Instance selector type for transparent @'Arbitrary'@ instances
data FWTransparentArbitrary = FWTransparentArbitrary deriving (Show, Read)
-- | Function identifier type for @'Apply'@.
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWArbitrary t a = FWArbitrary
-- | Function identifier type for @'Apply'@.
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWCoarbitrary t a = FWCoarbitrary
-- | * Default instance
instance TypeCast r FWTransparentArbitrary => FWArbitraryC (FW t a) r
-- | * Propagated instance
instance FWArbitraryC (FW s a) r => FWArbitraryC (FW (x :*: s) a) r
-- | * Specific @'FWDefaultArbitrary'@ instance
instance FWArbitraryC (FW (FWDefaultArbitrary :*: s) a) FWTransparentArbitrary
-- | * Specific @'FWTransparentArbitrary'@ instance
instance FWArbitraryC (FW (FWTransparentArbitrary :*: s) a)
FWTransparentArbitrary
-- | ** Implementation instance for @'Arbitrary'@ instance selection
instance Arbitrary a =>
Apply (Proxy (FWArbitrary t a)) (Proxy FWTransparentArbitrary)
(Gen (FW t a))
where
apply _ _ = fmap FlexiWrap arbitrary
-- | ** Implementation instance for @'Arbitrary'@ instance selection
instance Arbitrary a =>
Apply (Proxy (FWCoarbitrary t a)) (Proxy FWTransparentArbitrary)
(FW t a -> WrapCoarbitrary)
where
apply _ _ x = WrapCoarbitrary (coarbitrary $ unFlexiWrap x)
-- | * Coordinating instance of @'Arbitrary'@
instance forall t a r. (
Apply (Proxy (FWArbitrary t a)) (Proxy r) (Gen (FW t a)),
Apply (Proxy (FWCoarbitrary t a)) (Proxy r)
(FW t a -> WrapCoarbitrary),
FWArbitraryC (FW t a) r
) =>
Arbitrary (FW t a) where
arbitrary = apply (Proxy :: Proxy (FWArbitrary t a)) (Proxy :: Proxy r)
coarbitrary = unwrapCoarbitrary .
apply (Proxy :: Proxy (FWCoarbitrary t a)) (Proxy :: Proxy r)
-- Monoid
-- | Analysis class for @'Monoid'@ instance selection
-- You need a specific instance of this for any instance selectors
-- you may define.
class FWMonoid a r | a -> r
-- | Instance selector type for the default (transparent) @'Monoid'@
-- instances
data FWDefaultMonoid = FWDefaultMonoid deriving (Show, Read)
-- | Instance selector type for transparent @'Monoid'@ instances
data FWTransparentMonoid = FWTransparentMonoid deriving (Show, Read)
-- | Instance selector type for dual @'Monoid'@ instances,
-- obtained by swapping the arguments of 'mappend'.
data FWDualMonoid = FWDualMonoid deriving (Show, Read)
-- Internal version of FWDualMonoid, capturing the subsequent
-- instance selectors
data FWDualMonoidI s = FWDualMonoidI deriving (Show, Read)
-- | Instance selector type for instances of the @'Monoid'@ of
-- endomorphisms under composition.
data FWEndoMonoid = FWEndoMonoid deriving (Show, Read)
-- | Instance selector type for instances of the Boolean
-- @'Monoid'@ under conjunction.
data FWAllMonoid = FWAllMonoid deriving (Show, Read)
-- | Instance selector type for instances of the Boolean
-- @'Monoid'@ under disjunction.
data FWAnyMonoid = FWAnyMonoid deriving (Show, Read)
-- | Instance selector type for instances of a numeric
-- @'Monoid'@ under addition.
data FWSumMonoid = FWSumMonoid deriving (Show, Read)
-- | Instance selector type for instances of a numeric
-- @'Monoid'@ under multiplication.
data FWProductMonoid = FWProductMonoid deriving (Show, Read)
-- | Instance selector type for instances of a
-- Maybe @'Monoid'@ returning the leftmost non-Nothing value.
data FWFirstMonoid = FWFirstMonoid deriving (Show, Read)
-- | Instance selector type for instances of a
-- Maybe @'Monoid'@ returning the rightmost non-Nothing value.
data FWLastMonoid = FWLastMonoid deriving (Show, Read)
-- | Function identifier type for @'Apply'@.
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWMempty t a = FWMempty
-- | Function identifier type for @'Apply'@.
-- You need a corresponding instance of @'Apply'@ for any
-- instance selectors you may define.
data FWMappend t a = FWMappend
-- | * Default instance
instance TypeCast r FWTransparentMonoid => FWMonoid (FW t a) r
-- | * Propagated instance
instance FWMonoid (FW s a) r => FWMonoid (FW (x :*: s) a) r
-- | * Specific @'FWDefaultMonoid'@ instance
instance FWMonoid (FW (FWDefaultMonoid :*: s) a) FWTransparentMonoid
-- | * Specific @'FWTransparentMonoid'@ instance
instance FWMonoid (FW (FWTransparentMonoid :*: s) a) FWTransparentMonoid
-- | * Specific @'FWDualMonoid'@ instance
instance FWMonoid (FW (FWDualMonoid :*: s) a) (FWDualMonoidI s)
-- | * Specific @'FWEndoMonoid'@ instance
instance FWMonoid (FW (FWEndoMonoid :*: s) a) FWEndoMonoid
-- | * Specific @'FWAllMonoid'@ instance
instance FWMonoid (FW (FWAllMonoid :*: s) a) FWAllMonoid
-- | * Specific @'FWAnyMonoid'@ instance
instance FWMonoid (FW (FWAnyMonoid :*: s) a) FWAnyMonoid
-- | * Specific @'FWSumMonoid'@ instance
instance FWMonoid (FW (FWSumMonoid :*: s) a) FWSumMonoid
-- | * Specific @'FWProductMonoid'@ instance
instance FWMonoid (FW (FWProductMonoid :*: s) a) FWProductMonoid
-- | * Specific @'FWFirstMonoid'@ instance
instance FWMonoid (FW (FWFirstMonoid :*: s) a) FWFirstMonoid
-- | * Specific @'FWLastMonoid'@ instance
instance FWMonoid (FW (FWLastMonoid :*: s) a) FWLastMonoid
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Monoid a =>
Apply (Proxy (FWMempty t a)) (Proxy FWTransparentMonoid) (FW t a)
where
apply _ _ = FlexiWrap mempty
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Monoid a =>
Apply (Proxy (FWMappend t a)) (Proxy FWTransparentMonoid)
(FW t a -> FW t a -> FW t a)
where
apply _ _ = inFlexiWrap2 mappend
-- | ** Implementation instance for @'Monoid'@ instance selection
instance forall a t s. Monoid (FW s a) =>
Apply (Proxy (FWMempty t a)) (Proxy (FWDualMonoidI s)) (FW t a)
where
apply _ _ = FlexiWrap $ unFlexiWrap me
where
me = mempty :: FW s a
-- TODO: Move inCompose2R to Data.Flex.Utils
-- | ** Implementation instance for @'Monoid'@ instance selection
instance forall a t s. Monoid (FW s a) =>
Apply (Proxy (FWMappend t a)) (Proxy (FWDualMonoidI s))
(FW t a -> FW t a -> FW t a)
where
apply _ _ = inCompose2R unwrap wrap $ flip mappend
where
inCompose2R :: (forall v. p v -> q v) -> (q d -> e) ->
(q b -> q c -> q d) ->
(p b -> p c -> e)
inCompose2R down up = inCompose down $ inCompose down up
unwrap :: FW t b -> FW s b
unwrap = FlexiWrap . unFlexiWrap
wrap :: FW s a -> FW t a
wrap = FlexiWrap . unFlexiWrap
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMempty t (a -> a))) (Proxy FWEndoMonoid)
(FW t (a -> a))
where
apply _ _ = FlexiWrap id
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMappend t (a -> a))) (Proxy FWEndoMonoid)
(FW t (a -> a) -> FW t (a -> a) -> FW t (a -> a))
where
apply _ _ = inFlexiWrap2 (.)
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMempty t Bool)) (Proxy FWAllMonoid) (FW t Bool)
where
apply _ _ = FlexiWrap True
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMappend t Bool)) (Proxy FWAllMonoid)
(FW t Bool -> FW t Bool -> FW t Bool)
where
apply _ _ = inFlexiWrap2 (&&)
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMempty t Bool)) (Proxy FWAnyMonoid) (FW t Bool)
where
apply _ _ = FlexiWrap False
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMappend t Bool)) (Proxy FWAnyMonoid)
(FW t Bool -> FW t Bool -> FW t Bool)
where
apply _ _ = inFlexiWrap2 (||)
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Num a =>
Apply (Proxy (FWMempty t a)) (Proxy FWSumMonoid) (FW t a)
where
apply _ _ = FlexiWrap 0
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Num a =>
Apply (Proxy (FWMappend t a)) (Proxy FWSumMonoid)
(FW t a -> FW t a -> FW t a)
where
apply _ _ = inFlexiWrap2 (+)
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Num a =>
Apply (Proxy (FWMempty t a)) (Proxy FWProductMonoid) (FW t a)
where
apply _ _ = FlexiWrap 1
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Num a =>
Apply (Proxy (FWMappend t a)) (Proxy FWProductMonoid)
(FW t a -> FW t a -> FW t a)
where
apply _ _ = inFlexiWrap2 (*)
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMempty t (Maybe a))) (Proxy FWFirstMonoid)
(FW t (Maybe a))
where
apply _ _ = FlexiWrap Nothing
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMappend t (Maybe a))) (Proxy FWFirstMonoid)
(FW t (Maybe a) -> FW t (Maybe a) -> FW t (Maybe a))
where
apply _ _ = inFlexiWrap2 f
where
r@(Just _) `f` _ = r
Nothing `f` r = r
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMempty t (Maybe a))) (Proxy FWLastMonoid)
(FW t (Maybe a))
where
apply _ _ = FlexiWrap Nothing
-- | ** Implementation instance for @'Monoid'@ instance selection
instance Apply (Proxy (FWMappend t (Maybe a))) (Proxy FWLastMonoid)
(FW t (Maybe a) -> FW t (Maybe a) -> FW t (Maybe a))
where
apply _ _ = inFlexiWrap2 f
where
_ `f` r@(Just _) = r
r `f` Nothing = r
-- TODO: Min, Max monoids
-- | * Coordinating instance of @'Monoid'@
instance forall t a r. (
Apply (Proxy (FWMempty t a)) (Proxy r) (FW t a),
Apply (Proxy (FWMappend t a)) (Proxy r)
(FW t a -> FW t a -> FW t a),
FWMonoid (FW t a) r
) =>
Monoid (FW t a) where
mempty = apply (Proxy :: Proxy (FWMempty t a)) (Proxy :: Proxy r)
mappend = apply (Proxy :: Proxy (FWMappend t a)) (Proxy :: Proxy r)
{- TODO:
Num and it's subclasses
Bounded, Enum, Ix
Data, Typeable
Binary
NFData
-}
-- end FlexiWrap
-- vim: expandtab:tabstop=4:shiftwidth=4