我让用户输入一个功能,例如y = 2x ^ 2 + 3,作为字符串。我要做的是将该字符串输入TChart并输入TChart来绘制函数。
据我所知,TChart / TeeChart只会接受指定值的X值,例如: X为-10到10,因此每次都需要计算X值 - 这不是问题。
问题在于获得输入函数的每个部分并将X值代入每个部分。我找到的解决方法是让用户输入函数的每个部分的度,例如2对于X ^ 2,3对于X ^ 3等,但是有更清洁的方法吗?
如果我可以将输入的字符串转换为TeeChart可以接受的数学公式,那将是理想的结果。
答案 0 :(得分:3)
说你不能有效地使用外部单位会使你的问题在SO格式中无法回答,因为这个主题更广泛(更深入),可以用SO的Q& A格式轻松处理。所以以下是最好的概要:
如果你想或不得不写一个DIY表达评估器,一种方法是按以下步骤进行:
给自己写一个类,它将一个字符串作为输入并将其剪切成一系列符号,也就是代表表达式组成部分的“标记”,例如数字,运算符,括号,函数名称,名称变量等;这些令牌本身可能是记录或类实例,并且需要包括用于存储与特定符号相关联的值的机制(例如,表示输入中的数字的令牌)。此步骤称为“令牌化”或“lexing”。将生成的符号列表存储在列表或类似结构中。此类需要实现一种机制来从列表中检索下一个符号(通常,此方法称为“NextToken”)并指示是否还有符号。这个类还需要一种机制来“放回”一个符号(或者,相当于“窥视”当前符号之后的符号)。
然后,给自己写一个s / ware机器,它获取标记符号并“评估”符号列表以产生你所追求的(数学)结果。该步骤比标记化步骤难一个数量级或两个数量级。有很多方法可以做到这一点。正如我之前所说的那样,如果你之前从未做过这样的事情,那么递归下降解析器可能是最容易处理的方法。教科书中有无数的例子,但这里有一篇关于Delphi实现的文章的链接,作为一个介绍应该是可以理解的:
http://www8.umoncton.ca/umcm-deslierres_michel/Calcs/ParsingMathExpr-1.html
那篇文章首先指出有许多已有的Delphi表达式评估器,但指出它们不一定是想要学习如何编写评估器/解析器而不是仅仅使用它的人的最佳起点。相反,它通过编码评估器来实现这个简单的表达式语法:
表达式:术语|术语+术语|期限
术语:因素| factor * factor |因子/因子
因素:数量| (表达)| +因子| - 因素
(竖线|表示'或')
该文章有第二部分的链接,显示必须向评估者添加取幂 - 这比听起来更棘手,涉及歧义问题:例如:如何评估 - 以及写作是什么意思 - 像
这样的表达式的x ^ý^ Z
?这涉及到“关联性”的问题:大多数操作符都是“左联想”,这意味着它们与它们左边的内容绑定得比它们右边的更紧密。指数运算符是反向的一个例子,其中运算符与其右侧的运算符绑定得更紧密。
玩得开心!
顺便说一下,您曾经看过使用“分流场算法”实现评估器的建议
http://en.wikipedia.org/wiki/Shunting-yard_algorithm
转换运算符位于操作数之间的“中缀”表达式,如1 + 3 * 4到RPN(反向波兰表示法),用于较旧的HP计算器。这样做的原因是RPN可以更有效地评估中缀等价物的表达式。 Ymmv,但我个人发现正确实现SY算法实际上比学习如何在表达式/ term / factor样式中编写求值器更为棘手。
Fwiw,RPN是Forth编程语言http://en.wikipedia.org/wiki/Forth_%28programming_language%29的基础,所以如果你愿意,你可以在Delphi中编写一个Forth实现!