{-# LANGUAGE Safe #-}
module Base.Positional (
Positional(..),
alwaysPair,
processPairs,
processPairs_,
processPairsM,
processPairsT,
) where
import Control.Monad.Trans (MonadTrans(..))
import Base.CompilerError
import Base.Mergeable
newtype Positional a =
Positional {
Positional a -> [a]
pValues :: [a]
}
deriving (Positional a -> Positional a -> Bool
(Positional a -> Positional a -> Bool)
-> (Positional a -> Positional a -> Bool) -> Eq (Positional a)
forall a. Eq a => Positional a -> Positional a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: Positional a -> Positional a -> Bool
$c/= :: forall a. Eq a => Positional a -> Positional a -> Bool
== :: Positional a -> Positional a -> Bool
$c== :: forall a. Eq a => Positional a -> Positional a -> Bool
Eq,Eq (Positional a)
Eq (Positional a)
-> (Positional a -> Positional a -> Ordering)
-> (Positional a -> Positional a -> Bool)
-> (Positional a -> Positional a -> Bool)
-> (Positional a -> Positional a -> Bool)
-> (Positional a -> Positional a -> Bool)
-> (Positional a -> Positional a -> Positional a)
-> (Positional a -> Positional a -> Positional a)
-> Ord (Positional a)
Positional a -> Positional a -> Bool
Positional a -> Positional a -> Ordering
Positional a -> Positional a -> Positional 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 (Positional a)
forall a. Ord a => Positional a -> Positional a -> Bool
forall a. Ord a => Positional a -> Positional a -> Ordering
forall a. Ord a => Positional a -> Positional a -> Positional a
min :: Positional a -> Positional a -> Positional a
$cmin :: forall a. Ord a => Positional a -> Positional a -> Positional a
max :: Positional a -> Positional a -> Positional a
$cmax :: forall a. Ord a => Positional a -> Positional a -> Positional a
>= :: Positional a -> Positional a -> Bool
$c>= :: forall a. Ord a => Positional a -> Positional a -> Bool
> :: Positional a -> Positional a -> Bool
$c> :: forall a. Ord a => Positional a -> Positional a -> Bool
<= :: Positional a -> Positional a -> Bool
$c<= :: forall a. Ord a => Positional a -> Positional a -> Bool
< :: Positional a -> Positional a -> Bool
$c< :: forall a. Ord a => Positional a -> Positional a -> Bool
compare :: Positional a -> Positional a -> Ordering
$ccompare :: forall a. Ord a => Positional a -> Positional a -> Ordering
$cp1Ord :: forall a. Ord a => Eq (Positional a)
Ord,Int -> Positional a -> ShowS
[Positional a] -> ShowS
Positional a -> String
(Int -> Positional a -> ShowS)
-> (Positional a -> String)
-> ([Positional a] -> ShowS)
-> Show (Positional a)
forall a. Show a => Int -> Positional a -> ShowS
forall a. Show a => [Positional a] -> ShowS
forall a. Show a => Positional a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [Positional a] -> ShowS
$cshowList :: forall a. Show a => [Positional a] -> ShowS
show :: Positional a -> String
$cshow :: forall a. Show a => Positional a -> String
showsPrec :: Int -> Positional a -> ShowS
$cshowsPrec :: forall a. Show a => Int -> Positional a -> ShowS
Show)
instance Functor Positional where
fmap :: (a -> b) -> Positional a -> Positional b
fmap a -> b
f = [b] -> Positional b
forall a. [a] -> Positional a
Positional ([b] -> Positional b)
-> (Positional a -> [b]) -> Positional a -> Positional b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> b
f ([a] -> [b]) -> (Positional a -> [a]) -> Positional a -> [b]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Positional a -> [a]
forall a. Positional a -> [a]
pValues
alwaysPair :: Monad m => a -> b -> m (a,b)
alwaysPair :: a -> b -> m (a, b)
alwaysPair a
x b
y = (a, b) -> m (a, b)
forall (m :: * -> *) a. Monad m => a -> m a
return (a
x,b
y)
processPairs :: (Show a, Show b, CollectErrorsM m) =>
(a -> b -> m c) -> Positional a -> Positional b -> m [c]
processPairs :: (a -> b -> m c) -> Positional a -> Positional b -> m [c]
processPairs a -> b -> m c
f (Positional [a]
ps1) (Positional [b]
ps2)
| [a] -> Int
forall (t :: * -> *) a. Foldable t => t a -> Int
length [a]
ps1 Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== [b] -> Int
forall (t :: * -> *) a. Foldable t => t a -> Int
length [b]
ps2 =
((a, b) -> m c) -> [(a, b)] -> m [c]
forall (m :: * -> *) a b.
CollectErrorsM m =>
(a -> m b) -> [a] -> m [b]
mapCompilerM ((a -> b -> m c) -> (a, b) -> m c
forall a b c. (a -> b -> c) -> (a, b) -> c
uncurry a -> b -> m c
f) ([a] -> [b] -> [(a, b)]
forall a b. [a] -> [b] -> [(a, b)]
zip [a]
ps1 [b]
ps2)
| Bool
otherwise = [a] -> [b] -> m [c]
forall a b (m :: * -> *) c.
(Show a, Show b, ErrorContextM m) =>
[a] -> [b] -> m c
mismatchError [a]
ps1 [b]
ps2
processPairsM :: (Show a, Show b, Mergeable c, CollectErrorsM m) =>
(a -> b -> m c) -> Positional a -> Positional b -> m c
processPairsM :: (a -> b -> m c) -> Positional a -> Positional b -> m c
processPairsM a -> b -> m c
f Positional a
x Positional b
y = ([c] -> c) -> m [c] -> m c
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap [c] -> c
forall a (f :: * -> *). (Mergeable a, Foldable f) => f a -> a
mergeAll (m [c] -> m c) -> m [c] -> m c
forall a b. (a -> b) -> a -> b
$ (a -> b -> m c) -> Positional a -> Positional b -> m [c]
forall a b (m :: * -> *) c.
(Show a, Show b, CollectErrorsM m) =>
(a -> b -> m c) -> Positional a -> Positional b -> m [c]
processPairs a -> b -> m c
f Positional a
x Positional b
y
processPairs_ :: (Show a, Show b, CollectErrorsM m) =>
(a -> b -> m c) -> Positional a -> Positional b -> m ()
processPairs_ :: (a -> b -> m c) -> Positional a -> Positional b -> m ()
processPairs_ a -> b -> m c
f Positional a
xs Positional b
ys = (a -> b -> m c) -> Positional a -> Positional b -> m [c]
forall a b (m :: * -> *) c.
(Show a, Show b, CollectErrorsM m) =>
(a -> b -> m c) -> Positional a -> Positional b -> m [c]
processPairs a -> b -> m c
f Positional a
xs Positional b
ys m [c] -> m () -> m ()
forall (m :: * -> *) a b. Monad m => m a -> m b -> m b
>> () -> m ()
forall (m :: * -> *) a. Monad m => a -> m a
return ()
processPairsT :: (MonadTrans t, Monad (t m), Show a, Show b, ErrorContextM m) =>
(a -> b -> t m c) -> Positional a -> Positional b -> t m [c]
processPairsT :: (a -> b -> t m c) -> Positional a -> Positional b -> t m [c]
processPairsT a -> b -> t m c
f (Positional [a]
ps1) (Positional [b]
ps2)
| [a] -> Int
forall (t :: * -> *) a. Foldable t => t a -> Int
length [a]
ps1 Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== [b] -> Int
forall (t :: * -> *) a. Foldable t => t a -> Int
length [b]
ps2 =
[t m c] -> t m [c]
forall (t :: * -> *) (m :: * -> *) a.
(Traversable t, Monad m) =>
t (m a) -> m (t a)
sequence ([t m c] -> t m [c]) -> [t m c] -> t m [c]
forall a b. (a -> b) -> a -> b
$ ((a, b) -> t m c) -> [(a, b)] -> [t m c]
forall a b. (a -> b) -> [a] -> [b]
map ((a -> b -> t m c) -> (a, b) -> t m c
forall a b c. (a -> b -> c) -> (a, b) -> c
uncurry a -> b -> t m c
f) ([a] -> [b] -> [(a, b)]
forall a b. [a] -> [b] -> [(a, b)]
zip [a]
ps1 [b]
ps2)
| Bool
otherwise = m [c] -> t m [c]
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
lift (m [c] -> t m [c]) -> m [c] -> t m [c]
forall a b. (a -> b) -> a -> b
$ [a] -> [b] -> m [c]
forall a b (m :: * -> *) c.
(Show a, Show b, ErrorContextM m) =>
[a] -> [b] -> m c
mismatchError [a]
ps1 [b]
ps2
mismatchError :: (Show a, Show b, ErrorContextM m) => [a] -> [b] -> m c
mismatchError :: [a] -> [b] -> m c
mismatchError [a]
ps1 [b]
ps2 = String -> m c
forall (m :: * -> *) a. ErrorContextM m => String -> m a
compilerErrorM (String -> m c) -> String -> m c
forall a b. (a -> b) -> a -> b
$ String
"Count mismatch: " String -> ShowS
forall a. [a] -> [a] -> [a]
++ [a] -> String
forall a. Show a => a -> String
show [a]
ps1 String -> ShowS
forall a. [a] -> [a] -> [a]
++
String
" (expected) vs. " String -> ShowS
forall a. [a] -> [a] -> [a]
++ [b] -> String
forall a. Show a => a -> String
show [b]
ps2 String -> ShowS
forall a. [a] -> [a] -> [a]
++ String
" (actual)"