又一个python解析器生成器
fastidious的Python项目详细描述
用法
从 计算器示例 。 要阅读该示例,请考虑regex,除了or拼写为 文字字符用引号括起来,我们可以引用其他规则。
#! /usr/bin/pythonfromfastidiousimportParserclassCalculator(Parser):# __grammar__ is the PEG definition. Each `rulename <- a rule`# adds a method `Calculator.rulename()`. This methods tries to# match the input at current position__grammar__=r""" # the label is ommited. `:expr` is equivalent to `expr:expr` eval <- :expr EOF {@expr} # action {on_expr} calls `Calculator.on_expr(self, value, first, rest)` # on match. `first` and `rest` args are the labeled parts of the rule term <- first:factor rest:( _ mult_op _ factor )* {on_expr} # Because the Parser has a method named `on_expr` ("on_" + rulename) # this method is the implicit action of this rule. We omitted {on_expr} expr <- _ first:term rest:( _ add_op _ term )* _ # there's no explicit or implicit action. These rules return their exact # matches add_op <- '+' / '-' mult_op <- '*' / '/' # action {@fact} means : return only the match of part labeled `fact`. factor <- ( '(' fact:expr ')' ) / fact:integer {@fact} integer <- '-'? [0-9]+ _ <- [ \n\t\r]* # this one is tricky. `.` means "any char". At EOF there's no char, # thus Not any char, thus `!.` EOF <- !. """defon_expr(self,value,first,rest):result=firstforrinrest:op=r[1]ifop=='+':result+=r[3]elifop=='-':result-=r[3]elifop=='*':result*=r[3]else:result/=r[3]returnresultdefon_integer(self,value):returnint(self.p_flatten(value))if__name__=="__main__":importsysc=Calculator("".join(sys.argv[1:]))result=c.eval()# because eval is the first rule defined in the grammar, it's the default rule.# We could call the classmethod `p_parse`:# result = Calculator.p_parse("".join(sys.argv[1:]))# The default entry point can be overriden setting the class attribute# `__default__`print(result)
那么您就拥有了一个成熟的、最先进的、仅限整数的计算器o/
examples/calculator.py "-21 * ( 3 + 1 ) / -2"42
继承
解析器可以继承规则。下面是一个严格测试的例子:
classParent(Parser):__grammar__=r""" some_as <- 'a'+ """classChild(Parent):__grammar__=r""" letters <- some_as some_bs EOF {p_flatten} some_bs <- 'b'+ EOF <- !. """assert(Child.p_parse("aabb")=="aabb")
在这里, child 继承了方法rule some\u as
规则也可以在子分析器中重写。
注意,在将继承解析为来自父级的规则时没有开销 复制到子对象中。
控制
我计划在profistious.contrib中添加一组可重用的规则来组成 解析器.< /P>
目前,只有urlparser提供了一个匹配url和 匹配时输出 urlparse.parseresult 。
如果您编写了一段有趣的代码,请发送拉取请求:)