我试图了解如何重新创建由grako生成的解析器解析的文档。
在深入到grako源代码中之后,我相信我终于理解了如何从AST返回到生成的文档。有谁能检查一下我以下的理解是否正确,并告诉我是否有更直接的方法?
grako.model.Node的子类),用于语法中的每个规则。每个类至少必须有一个构造函数,其中包含对应规则中每个命名元素的参数,并将其值存储在类属性中。grako.codegen.ModelRenderer的子类,为语法中的每个规则(或多或少)定义“代码”生成的模板。grako.codegen.CodeGenerator().render(...)提供由Node子类和包含模板的python模块组成的AST,以创建输出。这是对的吗?这看起来一点也不直观。
发布于 2016-02-24 14:34:31
如果您查看Grako本身是如何解析语法的,您会注意到步骤2类是由ModelBuilderSemantics后裔综合创建的:
# from grako/semantics.py
class GrakoSemantics(ModelBuilderSemantics):
def __init__(self, grammar_name):
super(GrakoSemantics, self).__init__(
baseType=grammars.Model,
types=grammars.Model.classes()
)
self.grammar_name = grammar_name
self.rules = OrderedDict()
...如果类不存在于types=参数中,则合成类。ModelBuilderSemantics所需要的只是每个语法规则都带有一个参数,该参数为相应的Node提供类名。
module::Module = .... ;或,
module(Module) = ... ;第三步是不可避免的,因为翻译必须指定“某处”。Grako的方法允许将str模板与CodeGenerator所做的分派相关联地指定,这是我首选的翻译方式。但是,当我只需要从模型中提取信息时,我就使用grako.model.DepthFirstNodeWalker,比如生成符号表或计算指标。
步骤3不能自动化,因为将源语言的语义映射到目标语言的语义需要脑力,即使源和目标是相同的。
您还可以像您所建议的那样,遍历parse()或grako.model.Node.asjson()生成的类似JSON的Python结构( AST),但是处理代码将充满if-then-elseif以区分一个字典和另一个字典,或者一个列表和另一个列表。对于模型,层次结构中的每个dict都有一个Python类作为类型。
最后,Grako并没有强加一种方法来创建被解析的东西的模型,也没有将它转换成其他的东西。在它的基本形式中,Grako提供了一个具体的语法树(CST)或一个抽象语法树(AST),如果元素命名使用得当的话。其他的一切都是由一个特定的语义类产生的,它可以是一个人想要的任何东西。
https://stackoverflow.com/questions/35565052
复制相似问题