diff --git a/experiments/DataDependent.hs b/experiments/Main.hs similarity index 50% rename from experiments/DataDependent.hs rename to experiments/Main.hs index 6c904fd..ec5d7c2 100644 --- a/experiments/DataDependent.hs +++ b/experiments/Main.hs @@ -1,6 +1,6 @@ {-# LANGUAGE DeriveFunctor #-} -import Control.Applicative -import Data.Char +import Control.Applicative ( asum, Alternative((<|>), empty, many) ) +import Data.Char ( digitToInt, intToDigit ) newtype Parser s a = Parser { parse :: String -> s -> [(a, String, s)] } deriving Functor @@ -22,22 +22,30 @@ char c = Parser $ \xs s -> c' : xs' | c == c' -> [(c, xs', s)] _ -> [] -put :: Parser s' s -> Parser s a -> Parser s' a +put :: Parser s' s -> Parser (s,s') a -> Parser s' a put (Parser p) (Parser q) = Parser $ \xs s -> do - (s', xs', _) <- p xs s - (x, xs'', _) <- q xs' s' - pure (x, xs'', s) + (s', xs', t') <- p xs s + (x, xs'', (_,t'')) <- q xs' (s',t') + pure (x, xs'', t'') modify :: (s -> [s]) -> Parser s () modify f = Parser $ \xs s -> [((), xs, s') | s' <- f s] -dependentReplicate :: Parser s Int -> Parser Int a -> Parser s [a] -dependentReplicate p1 p2 = put p1 rest where - rest = (:) <$ modify (\s -> [s | s > 0]) <*> p2 <* modify (\s -> [s - 1]) <*> rest - <|> [] <$ modify (\s -> [s | s == 0]) +under :: Parser t a -> Parser (s, t) a +under (Parser p) = Parser $ \xs (s0,t) -> do + (x, xs', t') <- p xs t + pure (x, xs', (s0, t')) + +dependentReplicate :: Parser s Int -> Parser s a -> Parser s [a] +dependentReplicate p1 p2 = put p1 $ + many (modify (\s -> [s | fst s > 0]) *> under p2 <* modify (\(s,t) -> [(s - 1, t)])) + <* modify (\s -> [s | fst s == 0]) digit :: Parser s Int digit = asum [digitToInt <$> char (intToDigit i) | i <- [0..9]] main :: IO () -main = print $ parse (dependentReplicate digit (char '.')) "4...." () \ No newline at end of file +main = do + print $ parse (dependentReplicate digit (char '.')) "4..." () + print $ parse (dependentReplicate digit (char '.')) "4...." () + print $ parse (dependentReplicate digit (char '.')) "4....." () \ No newline at end of file diff --git a/gigaparsec.cabal b/gigaparsec.cabal index 25491fe..a41ec39 100644 --- a/gigaparsec.cabal +++ b/gigaparsec.cabal @@ -42,7 +42,7 @@ executable gigaparsec-examples hs-source-dirs: examples build-depends: gigaparsec -executable gigaparsec-experiments-datadependent +executable gigaparsec-experiments import: common - main-is: DataDependent.hs + main-is: Main.hs hs-source-dirs: experiments \ No newline at end of file diff --git a/hie.yaml b/hie.yaml new file mode 100644 index 0000000..00e9758 --- /dev/null +++ b/hie.yaml @@ -0,0 +1,8 @@ +cradle: + cabal: + - path: "src/" + component: "lib:gigaparsec" + - path: "examples/" + component: "exe:gigaparsec-examples" + - path: "experiments/" + component: "exe:gigaparsec-experiments" \ No newline at end of file