繁体   English   中英

如何使用逻辑运算符评估前缀表达式

[英]how to evaluate prefix expression for with logical operator

我有一个带有多个AND和OR运算符的前缀表达式,创建的级别大于1,我编写的算法可以很好地处理单个深度,但将结果的深度大于1时搞砸了。我使用的是python

前缀列表:- ['OR', 'AND', '=', ['.', 'grade'], 12, '>=', ['.', 'gpa'], ['.', '$', 'GPA'], 'AND', '=', ['.', 'a'], ['.', 'b'], '>', ['.', 'c'], ['.', 'd']]

def prefix_evaluation(prefix_list):
    opstack = []
    operand_stk = []
    pending_opd = False
    for token in prefix_list:
        if token in operators:
            opstack.append(token)
            pending_opd = False
        else:
            operand = token
            if pending_opd:
                while len(operand_stk) > 0:
                    opd_1 = operand_stk.pop()
                    operator  = opstack.pop()
                    operand = [operator, opd_1, operand]
            operand_stk.append(operand)
            pending_opd = True
    return operand_stk.pop()

预期结果:

[ OR,
    [ AND,
         [ AND,
              [ '=', ['.', 'grade'], 12],
              [ '>=', ['.', 'gpa'], ['.', '$', 'GPA']]
         ]
         [ AND,
              ['=', ['.', 'a'], ['.', 'b']],
              ['>', ['.', 'c'], ['.', 'd']]
         ]
    ]
]

实际结果:

['OR',
     ['AND', 
           ['AND', 
                ['=', ['.', 'grade'], 12], 
                ['>=', ['.', 'gpa'], 
                ['.', '$', 'GPA']]], 
           ['=', ['.', 'a'], ['.', 'b']]],
     ['>', ['.', 'c'], ['.', 'd']]]

为了使列表更易读,我将所有操作数都替换为n ,例如12['.', 'grade']['.', 'c']等。 另外,我用=替换了所有算术运算符,例如'>=''>'

现在您的列表看起来像OR AND = nn = nn AND = nn = nn

我使用了圆,方,大括号来强调术语如何组合在一起-或应该组合在一起

在此处输入图片说明

(= nn)实际上是一个由一个运算符和两个操作数组成的列表,例如['>=', 12, 12]

显示期望结果和实际结果之间差异的图形透视图如下: 在此处输入图片说明

到程序解析子列表OR AND = nn = nn的那一刻,它将形成操作数[AND (= nn) (= nn)] (以及仍在运算符堆栈中的额外OR )。 如您所见,此操作数对于预期结果和实际结果都是通用的。

程序解析完子列表OR AND = nn = nn AND = nn (请注意额外的AND = nn )时,它将具有已经形成的[AND (= nn) (= nn)]操作数,以及新的运算符AND和操作数(=nn) 它将分组为{AND [AND (= nn) (= nn)] (= nn) } 这就是程序的工作方式,以及编写方式。 现在确实有一种方法可以告诉您的程序:嘿,还需要形成第二个[AND (= nn) (= nn)] ,然后再将两者与OR串联。

打个比方,这就像期望解析器逐个字符地读取,以意识到1 + 2 * 3不是(1 + 2)* 3,而是1+(2 * 3),除非您以某种方式指定乘法具有优先于加法。

这里的陷阱是算术和逻辑运算符都放在同一个篮子里。 难怪在构建表达式时它们具有相同的优先级(优先级)。

更好的方法是通过将算术表达式(= nn)和逻辑表达式( [AND E1 E2] )放在两个不同的堆栈中,以及用于基本操作数的第3个堆栈(如n区分它们。 还要将=等算术运算符与AND逻辑运算符放在不同的堆栈中。 而且只有现在,您可以施加规则, 即“ AND”运算符应仅链接两个算术或两个逻辑表达式,而不能将一个算术与一个逻辑表达式链接在一起 ,以避免出现当前输出并获得预期的输出。

但是我觉得堆栈方法很麻烦,最好像有人建议的那样使用递归。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM