{-# LANGUAGE ExistentialQuantification, StandaloneDeriving #-}
module Text.Parsec.Perm
( PermParser
, StreamPermParser
, permute
, (<||>), (<$$>)
, (<|?>), (<$?>)
) where
import Text.Parsec
import Control.Monad.Identity
import Data.Typeable ( Typeable )
#if !(MIN_VERSION_base(4,7,0))
import Data.Typeable ( Typeable3 )
#endif
infixl 1 <||>, <|?>
infixl 2 <$$>, <$?>
(<||>) :: (Stream s Identity tok) => StreamPermParser s st (a -> b) -> Parsec s st a -> StreamPermParser s st b
<||> :: forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> Parsec s st a -> StreamPermParser s st b
(<||>) StreamPermParser s st (a -> b)
perm Parsec s st a
p = forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> Parsec s st a -> StreamPermParser s st b
add StreamPermParser s st (a -> b)
perm Parsec s st a
p
(<$$>) :: (Stream s Identity tok) => (a -> b) -> Parsec s st a -> StreamPermParser s st b
<$$> :: forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> Parsec s st a -> StreamPermParser s st b
(<$$>) a -> b
f Parsec s st a
p = forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> StreamPermParser s st (a -> b)
newperm a -> b
f forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> Parsec s st a -> StreamPermParser s st b
<||> Parsec s st a
p
(<|?>) :: (Stream s Identity tok) => StreamPermParser s st (a -> b) -> (a, Parsec s st a) -> StreamPermParser s st b
<|?> :: forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> (a, Parsec s st a) -> StreamPermParser s st b
(<|?>) StreamPermParser s st (a -> b)
perm (a
x,Parsec s st a
p) = forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> a -> Parsec s st a -> StreamPermParser s st b
addopt StreamPermParser s st (a -> b)
perm a
x Parsec s st a
p
(<$?>) :: (Stream s Identity tok) => (a -> b) -> (a, Parsec s st a) -> StreamPermParser s st b
<$?> :: forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> (a, Parsec s st a) -> StreamPermParser s st b
(<$?>) a -> b
f (a
x,Parsec s st a
p) = forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> StreamPermParser s st (a -> b)
newperm a -> b
f forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> (a, Parsec s st a) -> StreamPermParser s st b
<|?> (a
x,Parsec s st a
p)
type PermParser tok st a = StreamPermParser String st a
data StreamPermParser s st a = Perm (Maybe a) [StreamBranch s st a]
#if MIN_VERSION_base(4,7,0)
deriving ( Typeable )
#else
deriving instance Typeable3 StreamPermParser
#endif
data StreamBranch s st a = forall b. Branch (StreamPermParser s st (b -> a)) (Parsec s st b)
#if MIN_VERSION_base(4,7,0)
deriving ( Typeable )
#else
deriving instance Typeable3 StreamBranch
#endif
permute :: (Stream s Identity tok) => StreamPermParser s st a -> Parsec s st a
permute :: forall s tok st a.
Stream s Identity tok =>
StreamPermParser s st a -> Parsec s st a
permute (Perm Maybe a
def [StreamBranch s st a]
xs)
= forall s (m :: * -> *) t u a.
Stream s m t =>
[ParsecT s u m a] -> ParsecT s u m a
choice (forall a b. (a -> b) -> [a] -> [b]
map forall {s} {tok} {st} {a}.
Stream s Identity tok =>
StreamBranch s st a -> ParsecDSL s st Identity a
branch [StreamBranch s st a]
xs forall a. [a] -> [a] -> [a]
++ [ParsecT s st Identity a]
empty)
where
empty :: [ParsecT s st Identity a]
empty
= case Maybe a
def of
Maybe a
Nothing -> []
Just a
x -> [forall (m :: * -> *) a. Monad m => a -> m a
return a
x]
branch :: StreamBranch s st a -> ParsecDSL s st Identity a
branch (Branch StreamPermParser s st (b -> a)
perm Parsec s st b
p)
= do{ b
x <- Parsec s st b
p
; b -> a
f <- forall s tok st a.
Stream s Identity tok =>
StreamPermParser s st a -> Parsec s st a
permute StreamPermParser s st (b -> a)
perm
; forall (m :: * -> *) a. Monad m => a -> m a
return (b -> a
f b
x)
}
newperm :: (Stream s Identity tok) => (a -> b) -> StreamPermParser s st (a -> b)
newperm :: forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> StreamPermParser s st (a -> b)
newperm a -> b
f
= forall s st a.
Maybe a -> [StreamBranch s st a] -> StreamPermParser s st a
Perm (forall a. a -> Maybe a
Just a -> b
f) []
add :: (Stream s Identity tok) => StreamPermParser s st (a -> b) -> Parsec s st a -> StreamPermParser s st b
add :: forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> Parsec s st a -> StreamPermParser s st b
add perm :: StreamPermParser s st (a -> b)
perm@(Perm Maybe (a -> b)
_mf [StreamBranch s st (a -> b)]
fs) Parsec s st a
p
= forall s st a.
Maybe a -> [StreamBranch s st a] -> StreamPermParser s st a
Perm forall a. Maybe a
Nothing (StreamBranch s st b
firstforall a. a -> [a] -> [a]
:forall a b. (a -> b) -> [a] -> [b]
map forall {tok} {a}.
Stream s Identity tok =>
StreamBranch s st (a -> a) -> StreamBranch s st a
insert [StreamBranch s st (a -> b)]
fs)
where
first :: StreamBranch s st b
first = forall s st a b.
StreamPermParser s st (b -> a)
-> Parsec s st b -> StreamBranch s st a
Branch StreamPermParser s st (a -> b)
perm Parsec s st a
p
insert :: StreamBranch s st (a -> a) -> StreamBranch s st a
insert (Branch StreamPermParser s st (b -> a -> a)
perm' Parsec s st b
p')
= forall s st a b.
StreamPermParser s st (b -> a)
-> Parsec s st b -> StreamBranch s st a
Branch (forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> Parsec s st a -> StreamPermParser s st b
add (forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> StreamPermParser s st a -> StreamPermParser s st b
mapPerms forall a b c. (a -> b -> c) -> b -> a -> c
flip StreamPermParser s st (b -> a -> a)
perm') Parsec s st a
p) Parsec s st b
p'
addopt :: (Stream s Identity tok) => StreamPermParser s st (a -> b) -> a -> Parsec s st a -> StreamPermParser s st b
addopt :: forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> a -> Parsec s st a -> StreamPermParser s st b
addopt perm :: StreamPermParser s st (a -> b)
perm@(Perm Maybe (a -> b)
mf [StreamBranch s st (a -> b)]
fs) a
x Parsec s st a
p
= forall s st a.
Maybe a -> [StreamBranch s st a] -> StreamPermParser s st a
Perm (forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap (forall a b. (a -> b) -> a -> b
$ a
x) Maybe (a -> b)
mf) (StreamBranch s st b
firstforall a. a -> [a] -> [a]
:forall a b. (a -> b) -> [a] -> [b]
map forall {tok} {a}.
Stream s Identity tok =>
StreamBranch s st (a -> a) -> StreamBranch s st a
insert [StreamBranch s st (a -> b)]
fs)
where
first :: StreamBranch s st b
first = forall s st a b.
StreamPermParser s st (b -> a)
-> Parsec s st b -> StreamBranch s st a
Branch StreamPermParser s st (a -> b)
perm Parsec s st a
p
insert :: StreamBranch s st (a -> a) -> StreamBranch s st a
insert (Branch StreamPermParser s st (b -> a -> a)
perm' Parsec s st b
p')
= forall s st a b.
StreamPermParser s st (b -> a)
-> Parsec s st b -> StreamBranch s st a
Branch (forall s tok st a b.
Stream s Identity tok =>
StreamPermParser s st (a -> b)
-> a -> Parsec s st a -> StreamPermParser s st b
addopt (forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> StreamPermParser s st a -> StreamPermParser s st b
mapPerms forall a b c. (a -> b -> c) -> b -> a -> c
flip StreamPermParser s st (b -> a -> a)
perm') a
x Parsec s st a
p) Parsec s st b
p'
mapPerms :: (Stream s Identity tok) => (a -> b) -> StreamPermParser s st a -> StreamPermParser s st b
mapPerms :: forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> StreamPermParser s st a -> StreamPermParser s st b
mapPerms a -> b
f (Perm Maybe a
x [StreamBranch s st a]
xs)
= forall s st a.
Maybe a -> [StreamBranch s st a] -> StreamPermParser s st a
Perm (forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> b
f Maybe a
x) (forall a b. (a -> b) -> [a] -> [b]
map forall {s} {tok} {st}.
Stream s Identity tok =>
StreamBranch s st a -> StreamBranch s st b
mapBranch [StreamBranch s st a]
xs)
where
mapBranch :: StreamBranch s st a -> StreamBranch s st b
mapBranch (Branch StreamPermParser s st (b -> a)
perm Parsec s st b
p)
= forall s st a b.
StreamPermParser s st (b -> a)
-> Parsec s st b -> StreamBranch s st a
Branch (forall s tok a b st.
Stream s Identity tok =>
(a -> b) -> StreamPermParser s st a -> StreamPermParser s st b
mapPerms (a -> b
fforall b c a. (b -> c) -> (a -> b) -> a -> c
.) StreamPermParser s st (b -> a)
perm) Parsec s st b
p