如何在将中缀表达式转换为反向波兰表示法时计算方法的参数数量

How to count number of arguments of a method while converting infix expression to reverse polish notation

我有如下表达。 最小值(最大值(平均值(平均值(4,2),2,3),总和(1,2))) 我已经实现了调车场算法来将中缀转换为逆波兰表示法。 我添加了带有两个参数的函数 MAX 、 MIN 和 AVG 。但是假设如果我想实现变量参数,那么我必须知道每个函数在中缀表达式中有多少个参数。 有人能告诉我如何修改调车场算法以包含否。将中缀转换为 rpn 时每个函数的参数?

所以如果你有 log max(1, 2, 3, 4, 5) 你会做:

log => push log to stack
max => push max to stack
( => push ( to stack
1 => push 1 to stack
, => pop top of stack to output => pop 1 to output
2 => push 2 to stack
, => pop 2 to output
...
=> end result: 1 2 3 4 5 max log

问题是您不知道有多少自变量属于 max 有多少自变量属于 log(对数可能也可能不以底数作为自变量)。

使用 wikipedia description,应该可以计算每个函数参数分隔符(逗号):如果你有 k 函数分隔符,那么你有 k + 1 个参数,所以你可以在上面输出一个1 2 3 4 5 max_5 log。注意在嵌套函数的情况下有不同的计数:

max(1, 2, log(3, 4), 5) => 1 2 3 4 log_2 5 max_4
                               ---------
             max has 4 arguments after evaluating log_2(3, 4)

max 标记有一个计数,log 函数有另一个计数。您需要跟踪堆栈中最顶层函数标记的计数,但也需要跟踪堆栈中所有其他函数标记的计数,因为您最终可能会恢复这些计数。

这就是我最终做到的。 当令牌是左括号时,我将它添加到输出队列。 然后,当转换或执行 RPN 输出时,遇到函数调用标记,我从堆栈中弹出项目,直到遇到左括号,丢弃它,并将其间的所有内容视为函数的参数。

可能不是一个很好的解决方案,但效果很好 :)

一个稍微整洁的解决方案是制作另一个堆栈。将当前令牌位置推入此堆栈以找到一个开放的括号。然后当找到一个右括号时,弹出第一个值并使用当前标记位置之间的差异来查找括号之间的参数总数。如果运算符是函数,则可以使用该值,否则将其丢弃。

我不确定我是否会将左括号推入输出堆栈。这意味着您将在堆栈中添加括号以进行 3 * ( 4 + 5 ) 之类的操作。 相反,我会有与该函数关联的逻辑:当您遇到 MAX 或 MIN 时,然后将标记标记(例如...“|”)推入堆栈。现在,当您评估时,您可以使用堆栈中的所有项目,直到第一个“|”作为函数的参数。