module Data.MediaBus.Basics.Series
( Series(..)
, _Next
, _Start
, type Series'
, AsSeries(..)
, AsSeriesStart(..)
, AsSeriesNext(..)
) where
import Control.DeepSeq
import Control.Lens
import Data.Bifunctor
import GHC.Generics (Generic)
import Test.QuickCheck
data Series a b
= Next { _seriesValue :: !b}
| Start { _seriesStartValue :: !a}
deriving (Eq, Generic)
makePrisms ''Series
type Series' a = Series a a
instance (NFData a, NFData b) =>
NFData (Series a b)
instance (Show a, Show b) =>
Show (Series a b) where
showsPrec d (Start !x) =
showParen (d > 10) $ showString "start: " . showsPrec 11 x
showsPrec d (Next !x) =
showParen (d > 10) $ showString "next: " . showsPrec 11 x
instance (Ord a, Ord b) =>
Ord (Series a b) where
compare (Next !l) (Next !r) = compare l r
compare _ _ = EQ
instance (Arbitrary a, Arbitrary b) =>
Arbitrary (Series a b) where
arbitrary = do
isNext <- choose (0.0, 1.0)
if isNext < (0.95 :: Double)
then Next <$> arbitrary
else Start <$> arbitrary
instance Functor (Series a) where
fmap = over _Next
instance Bifunctor Series where
first = over _Start
second = over _Next
class AsSeries s a b | s -> a, s -> b where
seriesStart' :: Prism' s a
seriesNext' :: Prism' s b
instance AsSeries (Either a b) a b where
seriesStart' = _Left
seriesNext' = _Right
instance AsSeries (Series a b) a b where
seriesNext' = _Next
seriesStart' = _Start
class (SetSeriesStart s (GetSeriesStart s) ~ s) =>
AsSeriesStart s where
type GetSeriesStart s
type SetSeriesStart s t
seriesStart :: Prism s (SetSeriesStart s n) (GetSeriesStart s) n
instance AsSeriesStart (Either a b) where
type GetSeriesStart (Either a b) = a
type SetSeriesStart (Either a b) n = (Either n b)
seriesStart = _Left
instance AsSeriesStart (Series a b) where
type GetSeriesStart (Series a b) = a
type SetSeriesStart (Series a b) n = (Series n b)
seriesStart = _Start
class (SetSeriesNext s (GetSeriesNext s) ~ s) =>
AsSeriesNext s where
type GetSeriesNext s
type SetSeriesNext s t
seriesNext :: Prism s (SetSeriesNext s n) (GetSeriesNext s) n
instance AsSeriesNext (Either a b) where
type GetSeriesNext (Either a b) = b
type SetSeriesNext (Either a b) n = (Either a n)
seriesNext = _Right
instance AsSeriesNext (Series a b) where
type GetSeriesNext (Series a b) = b
type SetSeriesNext (Series a b) n = (Series a n)
seriesNext = _Next