【问题标题】:PEG NodeVisitorPEG 节点访问者
【发布时间】:2019-03-28 15:30:13
【问题描述】:

想象一下像PEG 这样的小语法

from parsimonious.grammar import Grammar
from parsimonious.nodes import NodeVisitor

grammar = Grammar(
    r"""
    term    = lpar (number comma? ws?)+ rpar
    number  = ~"\d+"
    lpar    = "("
    rpar    = ")"
    comma   = ","
    ws      = ~"\s*"
    """
)

tree = grammar.parse("(5, 4, 3)")
print(tree)

哪些输出

<Node called "term" matching "(5, 4, 3)">
    <Node called "lpar" matching "(">
    <Node matching "5, 4, 3">
        <Node matching "5, ">
            <RegexNode called "number" matching "5">
            <Node matching ",">
                <Node called "comma" matching ",">
            <Node matching " ">
                <RegexNode called "ws" matching " ">
        <Node matching "4, ">
            <RegexNode called "number" matching "4">
            <Node matching ",">
                <Node called "comma" matching ",">
            <Node matching " ">
                <RegexNode called "ws" matching " ">
        <Node matching "3">
            <RegexNode called "number" matching "3">
            <Node matching "">
            <Node matching "">
                <RegexNode called "ws" matching "">
    <Node called "rpar" matching ")">

在本例中如何从term 获取number 正则表达式部分?我知道我可以使用 NodeVisitor 类并检查每个数字,但我想从 term 中获取正则表达式部分。

【问题讨论】:

    标签: python parsing peg


    【解决方案1】:

    使用NodeVisitor 类并沿此方向遍历树可能会更好,但这里有另一个简单的解决方案:

    from parsimonious.grammar import Grammar
    from parsimonious.nodes import NodeVisitor
    
    grammar = Grammar(
        r"""
        term    = lpar (number comma? ws?)+ rpar
        number  = ~"\d+"
        lpar    = "("
        rpar    = ")"
        comma   = ","
        ws      = ~"\s*"
        """
    )
    
    tree = grammar.parse("(5, 4, 3)")
    
    def walk(node):
        if node.expr_name == 'number':
            print(node)
        for child in node.children:
            walk(child)
    
    walk(tree)
    
    # <RegexNode called "number" matching "5">
    # <RegexNode called "number" matching "4">
    # <RegexNode called "number" matching "3">
    

    【讨论】:

    • 非常感谢,我现在正在使用组合。
    猜你喜欢
    • 2016-02-13
    • 1970-01-01
    • 2017-06-29
    • 2011-01-11
    • 2019-01-21
    • 2014-05-29
    • 2021-04-27
    • 1970-01-01
    相关资源
    最近更新 更多