我知道我们如何在转换为波兰表示法后评估表达式。但是我想知道如何评估这样的事情:
If a < b Then a + b Else a - b
a + b
如果条件a < b
为真,则发生,否则,如果a - b
计算为假。
语法在这里不是问题。因为我只需要算法来解决这个问题。我能够评估布尔和代数表达式。但是我该如何解决上述问题呢?
我知道我们如何在转换为波兰表示法后评估表达式。但是我想知道如何评估这样的事情:
If a < b Then a + b Else a - b
a + b
如果条件a < b
为真,则发生,否则,如果a - b
计算为假。
语法在这里不是问题。因为我只需要算法来解决这个问题。我能够评估布尔和代数表达式。但是我该如何解决上述问题呢?
基本上,您需要构建对三元运算符的支持。IE,目前你弹出一个运算符,然后在解析它之前等待2个连续值,如果你当前的操作是IF,你需要等待3,其他操作需要等待2。
要处理 if 语句,您可以根据 C++ 的三元运算符来考虑 if 语句。您希望语法支持哪种格式取决于您。
a < b ? a + b : a - b
您应该能够以当前评估算术运算的方式评估堆栈上的布尔运算符,因此 a < b 应该被推送为
< a b
if 可以用栈上自己的符号来表示,我们可以坚持使用 '?'。
? < a b
以及评估需要由另一个运算符分隔的 2 个可能条件,不妨使用 ':'
? < a b : + a b - a b
所以现在当你弹出“?”时,你会看到它是需要 3 个值的运算符,所以像往常一样把它放在一边,继续计算堆栈,直到你有 3 个值。':' 运算符应该是一个二元运算符,它只是将它的两个值都推回堆栈。
一旦你在堆栈上有 3 个值,你评估 ? 作为:
如果第一个值为 1,则压入第二个值,丢弃第三个值。
如果第一个值为 0,则丢弃第二个并推动第三个。
S-express 参考 LISP 语言:例如
(if (> a b) ; if-part
(+ a b) ; then-part
(- a b)) ; else-part
实际上,如果您只想评估这个简单的 if 语句,请将其标记化并评估它,但是如果您想评估更复杂的事情,例如嵌套 if then else、if with experssions、multiple else、变量赋值、类型……您需要使用一些解析器,比如LR 解析器。您可以使用例如Lex&Yacc为您自己的语言编写一个好的解析器。它们支持某种复杂的语法。但是,如果您想知道 LR 解析器(左右)是如何工作的,您应该阅读它们,并查看它们如何使用它们的表来读取标记并解析它们。例如,看看 wiki 页面,看看 LR 解析器表是如何工作的(它不仅仅是简单的堆栈,在这里也不容易描述)。
如果你的问题只是解析if
语句,你可以从解析器技术中作弊,你可以在 a < b 之后添加空的东西,这意味着一些动作,在之后添加空的东西else
,这也意味着一个动作。当您解析条件时,根据正确性或错误性,您将运行其中一项操作。顺便说一句,如果你想在 if 语句中解析表达式,你需要条件堆栈,这意味着类似于SLR table。
您需要将 a+b 或 ab 分配给某物吗?
你可以这样做:
int c = a < b ? a+b : a-b;
或者
int sign = a < b ? 1 : -1;
int c = a + (sign * b);