[commit: ghc] wip/std-hdr-llf: Text.ParserCombinators.ReadP: use NonEmpty in Final (2a0be14)
git at git.haskell.org
git at git.haskell.org
Thu Feb 21 15:13:22 UTC 2019
Repository : ssh://git@git.haskell.org/ghc
On branch : wip/std-hdr-llf
Link : http://ghc.haskell.org/trac/ghc/changeset/2a0be1468cf440547e2ceb93f0d01d23637affc6/ghc
>---------------------------------------------------------------
commit 2a0be1468cf440547e2ceb93f0d01d23637affc6
Author: Vaibhav Sagar <vaibhavsagar at gmail.com>
Date: Sun Feb 17 19:41:38 2019 -0500
Text.ParserCombinators.ReadP: use NonEmpty in Final
The `Final` constructor needed to maintain the invariant that the list
it is provided is always non-empty. Since NonEmpty is in `base` now, I
think it would be better to use it for this purpose.
>---------------------------------------------------------------
2a0be1468cf440547e2ceb93f0d01d23637affc6
libraries/base/Text/ParserCombinators/ReadP.hs | 41 ++++++++++++++------------
1 file changed, 22 insertions(+), 19 deletions(-)
diff --git a/libraries/base/Text/ParserCombinators/ReadP.hs b/libraries/base/Text/ParserCombinators/ReadP.hs
index 2f36439..e28f32d 100644
--- a/libraries/base/Text/ParserCombinators/ReadP.hs
+++ b/libraries/base/Text/ParserCombinators/ReadP.hs
@@ -99,7 +99,7 @@ data P a
| Look (String -> P a)
| Fail
| Result a (P a)
- | Final [(a,String)] -- invariant: list is non-empty!
+ | Final (NonEmpty (a,String))
deriving Functor -- ^ @since 4.8.0.0
-- Monad, MonadPlus
@@ -114,11 +114,11 @@ instance MonadPlus P
-- | @since 2.01
instance Monad P where
- (Get f) >>= k = Get (\c -> f c >>= k)
- (Look f) >>= k = Look (\s -> f s >>= k)
- Fail >>= _ = Fail
- (Result x p) >>= k = k x <|> (p >>= k)
- (Final r) >>= k = final [ys' | (x,s) <- r, ys' <- run (k x) s]
+ (Get f) >>= k = Get (\c -> f c >>= k)
+ (Look f) >>= k = Look (\s -> f s >>= k)
+ Fail >>= _ = Fail
+ (Result x p) >>= k = k x <|> (p >>= k)
+ (Final (r:|rs)) >>= k = final [ys' | (x,s) <- (r:rs), ys' <- run (k x) s]
fail _ = Fail
@@ -144,11 +144,15 @@ instance Alternative P where
-- two finals are combined
-- final + look becomes one look and one final (=optimization)
-- final + sthg else becomes one look and one final
- Final r <|> Final t = Final (r ++ t)
- Final r <|> Look f = Look (\s -> Final (r ++ run (f s) s))
- Final r <|> p = Look (\s -> Final (r ++ run p s))
- Look f <|> Final r = Look (\s -> Final (run (f s) s ++ r))
- p <|> Final r = Look (\s -> Final (run p s ++ r))
+ Final r <|> Final t = Final (r <> t)
+ Final (r:|rs) <|> Look f = Look (\s -> Final (r:|(rs ++ run (f s) s)))
+ Final (r:|rs) <|> p = Look (\s -> Final (r:|(rs ++ run p s)))
+ Look f <|> Final r = Look (\s -> Final (case run (f s) s of
+ [] -> r
+ (x:xs) -> (x:|xs) <> r))
+ p <|> Final r = Look (\s -> Final (case run p s of
+ [] -> r
+ (x:xs) -> (x:|xs) <> r))
-- two looks are combined (=optimization)
-- look + sthg else floats upwards
@@ -192,16 +196,15 @@ instance MonadPlus ReadP
-- Operations over P
final :: [(a,String)] -> P a
--- Maintains invariant for Final constructor
-final [] = Fail
-final r = Final r
+final [] = Fail
+final (r:rs) = Final (r:|rs)
run :: P a -> ReadS a
-run (Get f) (c:s) = run (f c) s
-run (Look f) s = run (f s) s
-run (Result x p) s = (x,s) : run p s
-run (Final r) _ = r
-run _ _ = []
+run (Get f) (c:s) = run (f c) s
+run (Look f) s = run (f s) s
+run (Result x p) s = (x,s) : run p s
+run (Final (r:|rs)) _ = (r:rs)
+run _ _ = []
-- ---------------------------------------------------------------------------
-- Operations over ReadP
More information about the ghc-commits
mailing list