From bda57df5dab328e0940cfec6673590a528cfc64a Mon Sep 17 00:00:00 2001 From: Raphael Amiard Date: Tue, 8 Nov 2016 19:01:18 +0100 Subject: [PATCH] PB08-014: Add Pick utility parser Change-Id: I6755a1753bd5312620cdcbf92b4d332a57e2037f --- langkit/parsers.py | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/langkit/parsers.py b/langkit/parsers.py index ef1e31108..2055437b7 100644 --- a/langkit/parsers.py +++ b/langkit/parsers.py @@ -633,6 +633,32 @@ def always_make_progress(parser): return not isinstance(parser, (Opt, Null)) +def Pick(*parsers): + """ + Utility around Row and Extract, that will automatically scan a Row, remove + tokens and ignored sub parses, and extract the only significant sub-result. + + If there are several significant sub-results, raises an error. + """ + parsers = [resolve(p) for p in parsers if p] + pick_parser_idx = -1 + ignore = (Tok, Discard) + for i, p in enumerate(parsers): + if (isinstance(p, ignore) + or isinstance(p, Opt) and isinstance(p.parser, ignore)): + continue + check_source_language( + pick_parser_idx == -1, + "Pick parser can have only one sub-parser that is not a token" + ) + pick_parser_idx = i + + if pick_parser_idx == -1: + return Row(*parsers) + else: + return Row(*parsers)[pick_parser_idx] + + class Row(Parser): """Parser that matches a what sub-parsers match in sequence."""