Mercurial > lbo > hg > pcombinators
changeset 52:bc662ab63361 draft
Introduce new guarantee (None leaves state untouched) and remove many holds
author | Lewin Bormann <lbo@spheniscida.de> |
---|---|
date | Fri, 24 May 2019 00:07:15 +0200 |
parents | f5cfdd80cfe7 |
children | 2202ec2712c8 |
files | pcombinators/combinators.py |
diffstat | 1 files changed, 5 insertions(+), 9 deletions(-) [+] |
line wrap: on
line diff
--- a/pcombinators/combinators.py Thu May 23 22:56:33 2019 +0200 +++ b/pcombinators/combinators.py Fri May 24 00:07:15 2019 +0200 @@ -15,6 +15,8 @@ def parse(self, st): """Call parse() on any class inheriting from this one. It will consume the ParseState st and return the parse result (depending on the parsers used). + + None indicates a failed parse. In this case, st must be returned with unmodified position. """ return (None, st) @@ -64,17 +66,13 @@ self._transform = tf def parse(self, st): - hold = st.hold() r, st2 = self._inner.parse(st) if r is None: - st.reset(hold) return None, st try: r2 = self._transform(r) - st2.release(hold) return r2, st2 except Exception as e: - st.reset(hold) raise Exception('{} (at {} (col {}))'.format(e, st, st.index())) class _Sequence(Parser): @@ -99,12 +97,10 @@ def parse(self, st): results = [] - hold = st.hold() + hold = st.hold() if self._atomic else None for p in self._parsers: - before = st.hold() result, st2 = p.parse(st) if result is None: - st.reset(before) if self._atomic: st.reset(hold) return None, st @@ -112,8 +108,8 @@ if result is not SKIP_MARKER: results.append(result) st = st2 - st.release(before) - st.release(hold) + if self._atomic: + st.release(hold) return results, st2