感谢阅读。我真的需要一些帮助。我遇到了一个问题,涉及我使用递归方法来存储用户输入的完全标记的前缀表达式。在这个特定的例子中,数字用符号" n"标识,而符号等就像它们一样。所以,例如,这个:
%18 + 14 /(12 - 11) - 1183%17
将输入到命令提示符中:
现在,在项目早期,我的任务是存储一个中缀表达式,但是从已经构建的代码中获得了很多帮助。所以,这就是我对处理完全带括号的中缀函数所拥有的。我必须使用类似的方式创建一个方法(实际上在同一个文件中),然后从那里开始使用它。我已经掌握了打印功能,所以我真的只是想让存储空间正常运行。这是读取中缀表达式的代码:
Expr * readFPInfix(std::istream & infile)
{
static std::string ops("*+/%-");
char symbol;
infile >> symbol;
if (symbol == 'n')
{
long number;
infile >> number;
return new Atom(number);
}
else if (symbol == '(')
{
Expr * left = readFPInfix(infile);
char op;
infile >> op;
if (ops.find(op) == std::string::npos) {
std::cout << "Unknown operator symbol '" << op << "'" << std::endl;
system("pause");
exit(0);
}
Expr * right = readFPInfix(infile);
infile >> symbol;
// read the ending right parenthesis
if (symbol != ')') {
std::cout << "Invalid symbol '" << symbol << "': ')' expected" << std::endl;
system("pause");
exit(0);
}
switch (op)
{
case '*':
return new Times(left, right);
case '+':
return new Plus(left, right);
case '/':
return new Divide(left, right);
case '%':
return new Mod(left, right);
case '-':
return new Subtract(left, right);
default:
std::cout << "Read error" << std::endl;
system("pause");
exit(0);
}
}
else
{
std::cout << "Invalid symbol '" << symbol << "': 'n' or '(' expected" << std::endl;
system("pause");
exit(0);
}
}
现在,我假设我们必须使用相同的东西,所以我的主要问题是阅读该死的表达。我知道在这种方法中我们会逐个符号地读取它,然后根据提示测试该符号,以测试它是运算符还是数字。好吧,很酷。但是我如何左右移动,所以我可以输入类似Plus(左,右)的东西。我真的很挣扎,所以任何帮助都会非常感激。
注意:这是一项家庭作业,所以如果有人给我答案,那就没问题了,或者伪代码也没关系。谢谢。
答案 0 :(得分:0)
现在......正如我上面所评论的,这不是我们简单地向您提供设计或编码的地方。但是,我认为我仍然可以解释中缀如何分解为左右操作数。
中缀只有两种类型的操作数:终端(常量或变量)和表达式。
每个表达式都具有相同的形式:
operator left-operand right-operand
事实证明,您可以使用以下两个规则轻松解析复杂表达式:每次敲击运算符时,都会启动一个新表达式(即进行递归调用)。让我们逐步介绍您给定示例的合法版本:
% 18 + 14 / - 12 11 % 1183 17
我们发现的第一件事是%;保存运算符,然后在剩余的字符串18 + 14 / - 12 11 % 1183 17
中查找左右操作数。左边是微不足道的;那里有一个不变的。
// expression 1
operator = '%'
left = '18'
right = '+ 14 / - 12 11 % 1183 17'
这为我们提供了完整的顶级表达。但是,我们仍然需要解析正确的操作数。这是另一种表达方式。将+
作为运算符存储并解析两个操作数。
同样,左派是微不足道的;右边是表达的其余部分:
// expression 2
operator = '+'
left = '14'
right = '/ - 12 11 % 1183 17'
同样,我们仍然需要解析正确的操作数。将/
作为操作员存放,并且......哈!这一次,左操作数是一个表达式。我们仍将整个字符串传递给表达式解析器。
// expression 3
operator = '/'
left = <something from> '- 12 11 % 1183 17'
right = <on hold>
到目前为止,我已经跳过了以下步骤。当我们进行递归调用时,我们传递整个表达式。左操作数评估将吃掉它需要的任何东西,剩下的就是正确的评估。让我们现在更仔细地看一下......
//表达式4 operator =' - ' 左= 12 对= 11 余数='%1183 17'
必须将此余数传递回调用实例以用于正确的运算符。找到左操作数(并将其评估为1)后,我们将返回到表达式3的解析:
// expression 3
operator = '/'
left = 1
right = '% 1183 17'
现在我们同样解析正确的字符串,得到1183%17或10的值。注意我并没有带我们通过这个表达式5;像表达式4一样,这是一个简单的操作,['%',1183,17]。
最后,我们返回表达式3并执行1/10(整数运算为此给出0)。那个0成为表达式2的右侧,我们评估14 + 0.最后,该结果成为表达式1的右侧,最终答案是18%14或4。
现在......你能从那里做编程吗?