grammatical-parsers-0.7: src/Text/Grampa/Internal/Storable.hs
{-# LANGUAGE FlexibleInstances, MultiParamTypeClasses #-}
module Text.Grampa.Internal.Storable (Storable(..), Storable1(..), Storable11(..),
Dependencies(..), ParserFlags(..)) where
import Data.Functor.Const (Const(Const, getConst))
import qualified Rank2
import Text.Grampa.Class (ParseFailure(ParseFailure))
import Text.Grampa.Internal (ResultList(ResultList), ResultsOfLength(ResultsOfLength),
ParserFlags (ParserFlags, nullable, dependsOn),
Dependencies (DynamicDependencies, StaticDependencies))
import qualified Text.Grampa.ContextFree.SortedMemoizing.Transformer as Transformer
class Storable s a where
store :: a -> s
reuse :: s -> a
class Storable1 s a where
store1 :: a -> s b
reuse1 :: s b -> a
class Storable11 s t where
store11 :: t a -> s b
reuse11 :: s b -> t a
instance Storable a a where
store = id
reuse = id
instance Storable1 (Const a) a where
store1 = Const
reuse1 = getConst
instance Storable1 s a => Storable11 s (Const a) where
store11 = store1 . getConst
reuse11 = Const . reuse1
instance (Storable1 f a, Rank2.Functor g) => Storable (g f) (g (Const a)) where
store = Rank2.fmap (store1 . getConst)
reuse = Rank2.fmap (Const . reuse1)
instance Ord s => Storable1 (ResultList g s) Bool where
store1 bit = ResultList [] (ParseFailure (if bit then 1 else 0) mempty [])
reuse1 (ResultList _ (ParseFailure pos _ _)) = pos /= 0
instance (Rank2.Functor g, Monoid s, Ord s) => Storable1 (ResultList g s) (ParserFlags g) where
store1 a = ResultList [store a] mempty
reuse1 (ResultList [s] _) = reuse s
instance (Rank2.Functor g, Monoid s, Ord s) => Storable (ResultsOfLength g s r) (ParserFlags g) where
store (ParserFlags n d) = ResultsOfLength (if n then 1 else 0) (store d) (pure $ error "unused")
reuse (ResultsOfLength n d _) = ParserFlags (n /= 0) (reuse d)
instance (Rank2.Functor g, Monoid s, Ord s) => Storable [(s, g (ResultList g s))] (Dependencies g) where
store DynamicDependencies = []
store (StaticDependencies deps) = [(mempty, store deps)]
reuse [] = DynamicDependencies
reuse [(_, deps)] = StaticDependencies (reuse deps)
instance Ord s => Storable1 (Transformer.ResultListT m g s) Bool where
store1 bit = Transformer.ResultList [] (ParseFailure (if bit then 1 else 0) mempty [])
reuse1 (Transformer.ResultList _ (ParseFailure pos _ _)) = pos /= 0
instance (Rank2.Functor g, Monoid s, Ord s) => Storable1 (Transformer.ResultListT m g s) (ParserFlags g) where
store1 a = Transformer.ResultList [store a] mempty
reuse1 (Transformer.ResultList [s] _) = reuse s
instance (Rank2.Functor g, Monoid s, Ord s) => Storable (Transformer.ResultsOfLengthT m g s r) (ParserFlags g) where
store = Transformer.ResultsOfLengthT . store
reuse = reuse . Transformer.getResultsOfLength
instance (Rank2.Functor g, Monoid s, Ord s) => Storable (Transformer.ResultsOfLength m g s r) (ParserFlags g) where
store (ParserFlags n d) = Transformer.ROL (if n then 1 else 0) (store d) (pure $ error "unused")
reuse (Transformer.ROL n d _) = ParserFlags (n /= 0) (reuse d)
instance (Rank2.Functor g, Monoid s, Ord s) => Storable [(s, g (Transformer.ResultListT m g s))] (Dependencies g) where
store DynamicDependencies = []
store (StaticDependencies deps) = [(mempty, store deps)]
reuse [] = DynamicDependencies
reuse [(_, deps)] = StaticDependencies (reuse deps)