代码之家  ›  专栏  ›  技术社区  ›  Jan

在ply-递归中允许语法构造?

  •  0
  • Jan  · 技术社区  · 5 年前

    这可能是以前问过,但我不知道要搜索什么,真的。假设我有一些字符串,我想用它构建一个解析器。

    我有弦 a OR b , b OR C 而且 a OR (b AND c) . 现在嵌套的括号给我带来了麻烦,我不知道如何构造适当的 p_* 功能。允许递归吗?如果是这样,怎么办?


    这就是我迄今为止所拥有的:
    import ply.lex as lex
    import ply.yacc as yacc
    
    # List of token names.   This is always required
    tokens = (
        'VARIABLE',
        'OR',
        'AND',
        'PAR_OPEN',
        'PAR_CLOSE',
    )
    
    # Regular expression rules for simple tokens
    t_ignore        = ' \t'
    t_VARIABLE      = r'\b[a-z]+\b'
    t_OR            = r'\bOR\b'
    t_AND           = r'\bAND\b'
    t_PAR_OPEN      = r'\('
    t_PAR_CLOSE     = r'\)'
    
    def t_error(t):
        print("Illegal character '%s'" % t.value[0])
        t.lexer.skip(1)
    
    # Build the lexer
    lexer = lex.lex()
    
    def p_term(p):
        '''term : VARIABLE OR VARIABLE
                | VARIABLE AND VARIABLE
                | PAR_OPEN VARIABLE AND VARIABLE PAR_CLOSE'''
    
        if p[2] == 'AND':
            p[0] = "".join([p[1], p[3]])
    
        for idx, val in enumerate(p):
            print(idx, val)
    
    def p_error(p):
        print("Syntax error in input!")
        print(p)
    
    
    parser = yacc.yacc()
    res = parser.parse("(a AND b)")
    print(res)
    

    我还想用例如 res = parser.parse("a OR (b AND c)") 但无济于事。


    P.S.:这是基于 another one's question ,真的。
    1 回复  |  直到 5 年前
        1
  •  1
  •   aghast    5 年前

    表达式中的括号很常见。我先给你介绍 the PLY documentation 它提供了一个嵌套表达式解析的示例。是的,递归就是答案。

    有几个短语用来表示“表达式的最小元素”。您可能会看到“atom”或“term”(缩写为“terminal”)或“primary expression”。

    在处理插入式子表达式时,通常采用这种方法。编写一个语法规则,统一各种低级事物(例如,字面数字和变量名),并在该点添加子表达式。

    在本例中,从ply docs, expression 是最高级的东西,支持加减。下一级是 term 它支持乘法和除法。最低级的东西是 factor 不支持任何操作,但统一了 NUMBER 加括号的子表达式。一个因素可能是 7 但也有可能 (7 + 2 * 3) .

     expression : expression + term
                | expression - term
                | term
    
     term       : term * factor
                | term / factor
                | factor
    
     factor     : NUMBER
                | ( expression )