module Language.Parser.Ptera.Scanner where

import           Language.Parser.Ptera.Prelude


type T = Scanner

class Monad m => Scanner posMark elem m | m -> posMark, m -> elem where
    consumeInput :: m (Maybe elem)
    getPosMark :: m posMark
    seekToPosMark :: posMark -> m ()
    scanMode :: ScanMode posMark -> m ()

data ScanMode posMark
    = ScanModeNoBack
    | ScanModeNeedBack posMark
    deriving (ScanMode posMark -> ScanMode posMark -> Bool
forall posMark.
Eq posMark =>
ScanMode posMark -> ScanMode posMark -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: ScanMode posMark -> ScanMode posMark -> Bool
$c/= :: forall posMark.
Eq posMark =>
ScanMode posMark -> ScanMode posMark -> Bool
== :: ScanMode posMark -> ScanMode posMark -> Bool
$c== :: forall posMark.
Eq posMark =>
ScanMode posMark -> ScanMode posMark -> Bool
Eq, Int -> ScanMode posMark -> ShowS
forall posMark. Show posMark => Int -> ScanMode posMark -> ShowS
forall posMark. Show posMark => [ScanMode posMark] -> ShowS
forall posMark. Show posMark => ScanMode posMark -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ScanMode posMark] -> ShowS
$cshowList :: forall posMark. Show posMark => [ScanMode posMark] -> ShowS
show :: ScanMode posMark -> String
$cshow :: forall posMark. Show posMark => ScanMode posMark -> String
showsPrec :: Int -> ScanMode posMark -> ShowS
$cshowsPrec :: forall posMark. Show posMark => Int -> ScanMode posMark -> ShowS
Show)


newtype ListScanner e a = ListScanner
    {
        forall e a. ListScanner e a -> State [e] a
unListScanner :: State [e] a
    }
    deriving (forall a b. a -> ListScanner e b -> ListScanner e a
forall a b. (a -> b) -> ListScanner e a -> ListScanner e b
forall e a b. a -> ListScanner e b -> ListScanner e a
forall e a b. (a -> b) -> ListScanner e a -> ListScanner e b
forall (f :: * -> *).
(forall a b. (a -> b) -> f a -> f b)
-> (forall a b. a -> f b -> f a) -> Functor f
<$ :: forall a b. a -> ListScanner e b -> ListScanner e a
$c<$ :: forall e a b. a -> ListScanner e b -> ListScanner e a
fmap :: forall a b. (a -> b) -> ListScanner e a -> ListScanner e b
$cfmap :: forall e a b. (a -> b) -> ListScanner e a -> ListScanner e b
Functor, forall e. Functor (ListScanner e)
forall a. a -> ListScanner e a
forall e a. a -> ListScanner e a
forall a b. ListScanner e a -> ListScanner e b -> ListScanner e a
forall a b. ListScanner e a -> ListScanner e b -> ListScanner e b
forall a b.
ListScanner e (a -> b) -> ListScanner e a -> ListScanner e b
forall e a b. ListScanner e a -> ListScanner e b -> ListScanner e a
forall e a b. ListScanner e a -> ListScanner e b -> ListScanner e b
forall e a b.
ListScanner e (a -> b) -> ListScanner e a -> ListScanner e b
forall a b c.
(a -> b -> c)
-> ListScanner e a -> ListScanner e b -> ListScanner e c
forall e a b c.
(a -> b -> c)
-> ListScanner e a -> ListScanner e b -> ListScanner e c
forall (f :: * -> *).
Functor f
-> (forall a. a -> f a)
-> (forall a b. f (a -> b) -> f a -> f b)
-> (forall a b c. (a -> b -> c) -> f a -> f b -> f c)
-> (forall a b. f a -> f b -> f b)
-> (forall a b. f a -> f b -> f a)
-> Applicative f
<* :: forall a b. ListScanner e a -> ListScanner e b -> ListScanner e a
$c<* :: forall e a b. ListScanner e a -> ListScanner e b -> ListScanner e a
*> :: forall a b. ListScanner e a -> ListScanner e b -> ListScanner e b
$c*> :: forall e a b. ListScanner e a -> ListScanner e b -> ListScanner e b
liftA2 :: forall a b c.
(a -> b -> c)
-> ListScanner e a -> ListScanner e b -> ListScanner e c
$cliftA2 :: forall e a b c.
(a -> b -> c)
-> ListScanner e a -> ListScanner e b -> ListScanner e c
<*> :: forall a b.
ListScanner e (a -> b) -> ListScanner e a -> ListScanner e b
$c<*> :: forall e a b.
ListScanner e (a -> b) -> ListScanner e a -> ListScanner e b
pure :: forall a. a -> ListScanner e a
$cpure :: forall e a. a -> ListScanner e a
Applicative, forall e. Applicative (ListScanner e)
forall a. a -> ListScanner e a
forall e a. a -> ListScanner e a
forall a b. ListScanner e a -> ListScanner e b -> ListScanner e b
forall a b.
ListScanner e a -> (a -> ListScanner e b) -> ListScanner e b
forall e a b. ListScanner e a -> ListScanner e b -> ListScanner e b
forall e a b.
ListScanner e a -> (a -> ListScanner e b) -> ListScanner e b
forall (m :: * -> *).
Applicative m
-> (forall a b. m a -> (a -> m b) -> m b)
-> (forall a b. m a -> m b -> m b)
-> (forall a. a -> m a)
-> Monad m
return :: forall a. a -> ListScanner e a
$creturn :: forall e a. a -> ListScanner e a
>> :: forall a b. ListScanner e a -> ListScanner e b -> ListScanner e b
$c>> :: forall e a b. ListScanner e a -> ListScanner e b -> ListScanner e b
>>= :: forall a b.
ListScanner e a -> (a -> ListScanner e b) -> ListScanner e b
$c>>= :: forall e a b.
ListScanner e a -> (a -> ListScanner e b) -> ListScanner e b
Monad) via State [e]

runListScanner :: ListScanner e a -> [e] -> a
runListScanner :: forall e a. ListScanner e a -> [e] -> a
runListScanner (ListScanner State [e] a
scanner) [e]
xs = forall s a. State s a -> s -> a
evalState State [e] a
scanner [e]
xs

instance Scanner [e] e (ListScanner e) where
    consumeInput :: ListScanner e (Maybe e)
consumeInput = forall e a. State [e] a -> ListScanner e a
ListScanner do
        forall (m :: * -> *) s. Monad m => StateT s m s
get forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= \case
            [] ->
                forall (f :: * -> *) a. Applicative f => a -> f a
pure forall a. Maybe a
Nothing
            e
x:[e]
xs -> do
                forall (m :: * -> *) s. Monad m => s -> StateT s m ()
put [e]
xs
                forall (f :: * -> *) a. Applicative f => a -> f a
pure do forall a. a -> Maybe a
Just e
x

    getPosMark :: ListScanner e [e]
getPosMark = forall e a. State [e] a -> ListScanner e a
ListScanner forall (m :: * -> *) s. Monad m => StateT s m s
get

    seekToPosMark :: [e] -> ListScanner e ()
seekToPosMark [e]
xs = forall e a. State [e] a -> ListScanner e a
ListScanner do forall (m :: * -> *) s. Monad m => s -> StateT s m ()
put [e]
xs

    scanMode :: ScanMode [e] -> ListScanner e ()
scanMode ScanMode [e]
_ = forall (f :: * -> *) a. Applicative f => a -> f a
pure ()