{-|
Module      : Stype censored types and typeclasses
Description : Statistical types
Copyright   : (c) NoviSci, Inc 2020
License     : BSD3
Maintainer  : bsaul@novisci.com

-}

{-# LANGUAGE Safe #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE DeriveGeneric #-}

module Stype.Numeric.Censored (
    Censorable(..)
  , MaybeCensored(..)
  , ParseIntervalError(..)
) where

import safe Data.Text                  
  -- ( Text, pack, unpack )
import safe GHC.Generics                 ( Generic )

-- | Data for censored data
data MaybeCensored a where
  IntervalCensored :: a -> a -> MaybeCensored a
  RightCensored :: a -> MaybeCensored a
  LeftCensored :: a -> MaybeCensored a
  Uncensored :: a -> MaybeCensored a
  deriving( MaybeCensored a -> MaybeCensored a -> Bool
(MaybeCensored a -> MaybeCensored a -> Bool)
-> (MaybeCensored a -> MaybeCensored a -> Bool)
-> Eq (MaybeCensored a)
forall a. Eq a => MaybeCensored a -> MaybeCensored a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: MaybeCensored a -> MaybeCensored a -> Bool
$c/= :: forall a. Eq a => MaybeCensored a -> MaybeCensored a -> Bool
== :: MaybeCensored a -> MaybeCensored a -> Bool
$c== :: forall a. Eq a => MaybeCensored a -> MaybeCensored a -> Bool
Eq, Int -> MaybeCensored a -> ShowS
[MaybeCensored a] -> ShowS
MaybeCensored a -> String
(Int -> MaybeCensored a -> ShowS)
-> (MaybeCensored a -> String)
-> ([MaybeCensored a] -> ShowS)
-> Show (MaybeCensored a)
forall a. Show a => Int -> MaybeCensored a -> ShowS
forall a. Show a => [MaybeCensored a] -> ShowS
forall a. Show a => MaybeCensored a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [MaybeCensored a] -> ShowS
$cshowList :: forall a. Show a => [MaybeCensored a] -> ShowS
show :: MaybeCensored a -> String
$cshow :: forall a. Show a => MaybeCensored a -> String
showsPrec :: Int -> MaybeCensored a -> ShowS
$cshowsPrec :: forall a. Show a => Int -> MaybeCensored a -> ShowS
Show, Eq (MaybeCensored a)
Eq (MaybeCensored a)
-> (MaybeCensored a -> MaybeCensored a -> Ordering)
-> (MaybeCensored a -> MaybeCensored a -> Bool)
-> (MaybeCensored a -> MaybeCensored a -> Bool)
-> (MaybeCensored a -> MaybeCensored a -> Bool)
-> (MaybeCensored a -> MaybeCensored a -> Bool)
-> (MaybeCensored a -> MaybeCensored a -> MaybeCensored a)
-> (MaybeCensored a -> MaybeCensored a -> MaybeCensored a)
-> Ord (MaybeCensored a)
MaybeCensored a -> MaybeCensored a -> Bool
MaybeCensored a -> MaybeCensored a -> Ordering
MaybeCensored a -> MaybeCensored a -> MaybeCensored a
forall a.
Eq a
-> (a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall a. Ord a => Eq (MaybeCensored a)
forall a. Ord a => MaybeCensored a -> MaybeCensored a -> Bool
forall a. Ord a => MaybeCensored a -> MaybeCensored a -> Ordering
forall a.
Ord a =>
MaybeCensored a -> MaybeCensored a -> MaybeCensored a
min :: MaybeCensored a -> MaybeCensored a -> MaybeCensored a
$cmin :: forall a.
Ord a =>
MaybeCensored a -> MaybeCensored a -> MaybeCensored a
max :: MaybeCensored a -> MaybeCensored a -> MaybeCensored a
$cmax :: forall a.
Ord a =>
MaybeCensored a -> MaybeCensored a -> MaybeCensored a
>= :: MaybeCensored a -> MaybeCensored a -> Bool
$c>= :: forall a. Ord a => MaybeCensored a -> MaybeCensored a -> Bool
> :: MaybeCensored a -> MaybeCensored a -> Bool
$c> :: forall a. Ord a => MaybeCensored a -> MaybeCensored a -> Bool
<= :: MaybeCensored a -> MaybeCensored a -> Bool
$c<= :: forall a. Ord a => MaybeCensored a -> MaybeCensored a -> Bool
< :: MaybeCensored a -> MaybeCensored a -> Bool
$c< :: forall a. Ord a => MaybeCensored a -> MaybeCensored a -> Bool
compare :: MaybeCensored a -> MaybeCensored a -> Ordering
$ccompare :: forall a. Ord a => MaybeCensored a -> MaybeCensored a -> Ordering
$cp1Ord :: forall a. Ord a => Eq (MaybeCensored a)
Ord, (forall x. MaybeCensored a -> Rep (MaybeCensored a) x)
-> (forall x. Rep (MaybeCensored a) x -> MaybeCensored a)
-> Generic (MaybeCensored a)
forall x. Rep (MaybeCensored a) x -> MaybeCensored a
forall x. MaybeCensored a -> Rep (MaybeCensored a) x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
forall a x. Rep (MaybeCensored a) x -> MaybeCensored a
forall a x. MaybeCensored a -> Rep (MaybeCensored a) x
$cto :: forall a x. Rep (MaybeCensored a) x -> MaybeCensored a
$cfrom :: forall a x. MaybeCensored a -> Rep (MaybeCensored a) x
Generic )

-- | A type to hold a reason that interval fails to parse.
newtype ParseIntervalError = ParseIntervalError Text
  deriving ( ParseIntervalError -> ParseIntervalError -> Bool
(ParseIntervalError -> ParseIntervalError -> Bool)
-> (ParseIntervalError -> ParseIntervalError -> Bool)
-> Eq ParseIntervalError
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: ParseIntervalError -> ParseIntervalError -> Bool
$c/= :: ParseIntervalError -> ParseIntervalError -> Bool
== :: ParseIntervalError -> ParseIntervalError -> Bool
$c== :: ParseIntervalError -> ParseIntervalError -> Bool
Eq, Int -> ParseIntervalError -> ShowS
[ParseIntervalError] -> ShowS
ParseIntervalError -> String
(Int -> ParseIntervalError -> ShowS)
-> (ParseIntervalError -> String)
-> ([ParseIntervalError] -> ShowS)
-> Show ParseIntervalError
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ParseIntervalError] -> ShowS
$cshowList :: [ParseIntervalError] -> ShowS
show :: ParseIntervalError -> String
$cshow :: ParseIntervalError -> String
showsPrec :: Int -> ParseIntervalError -> ShowS
$cshowsPrec :: Int -> ParseIntervalError -> ShowS
Show)

-- | A class to censor data
class (Ord a, Show a) => Censorable a where
 
  parseIntervalCensor :: a -> a -> Either ParseIntervalError (MaybeCensored a)
  parseIntervalCensor a
x a
y
    | a
x a -> a -> Bool
forall a. Ord a => a -> a -> Bool
< a
y = MaybeCensored a -> Either ParseIntervalError (MaybeCensored a)
forall a b. b -> Either a b
Right (MaybeCensored a -> Either ParseIntervalError (MaybeCensored a))
-> MaybeCensored a -> Either ParseIntervalError (MaybeCensored a)
forall a b. (a -> b) -> a -> b
$ a -> a -> MaybeCensored a
forall a. a -> a -> MaybeCensored a
IntervalCensored a
x a
y
    | Bool
otherwise = ParseIntervalError -> Either ParseIntervalError (MaybeCensored a)
forall a b. a -> Either a b
Left (ParseIntervalError -> Either ParseIntervalError (MaybeCensored a))
-> ParseIntervalError
-> Either ParseIntervalError (MaybeCensored a)
forall a b. (a -> b) -> a -> b
$ Text -> ParseIntervalError
ParseIntervalError ( String -> Text
pack (a -> String
forall a. Show a => a -> String
show a
y String -> ShowS
forall a. [a] -> [a] -> [a]
++ String
" < " String -> ShowS
forall a. [a] -> [a] -> [a]
++ a -> String
forall a. Show a => a -> String
show a
x) )

  rightCensor ::  a -> a -> MaybeCensored a
  rightCensor a
c a
t
    | a
c a -> a -> Bool
forall a. Ord a => a -> a -> Bool
< a
t     = a -> MaybeCensored a
forall a. a -> MaybeCensored a
RightCensored a
c
    | Bool
otherwise = a -> MaybeCensored a
forall a. a -> MaybeCensored a
Uncensored a
t

  leftCensor ::  a -> a -> MaybeCensored a
  leftCensor a
c a
t
    | a
c a -> a -> Bool
forall a. Ord a => a -> a -> Bool
>= a
t    = a -> MaybeCensored a
forall a. a -> MaybeCensored a
LeftCensored a
c
    | Bool
otherwise = a -> MaybeCensored a
forall a. a -> MaybeCensored a
Uncensored a
t