2011-10-05 138 views
3

我想评估用户在文本框中输入的数学表达式。我已经这样做了迄今解决数学表达式

string equation, finalString; 
equation = textBox1.Text; 
StringBuilder stringEvaluate = new StringBuilder(equation); 
stringEvaluate.Replace("sin", "math.sin"); 
stringEvaluate.Replace("cos", "math.cos"); 
stringEvaluate.Replace("tan", "math.tan"); 
stringEvaluate.Replace("log", "math.log10"); 
stringEvaluate.Replace("e^", "math.exp"); 
finalString = stringEvaluate.ToString(); 
StringBuilder replaceI = new StringBuilder(finalString); 
replaceI.Replace("x", "i"); 

double a; 
for (int i = 0; i<5 ; i++) 
{ 
    a = double.Parse(finalStringI); 
    if(a<0) 
    break; 
} 

当我运行该程序它给出了一个错误"Input string was not in a correct format."并突出a=double.Parse(finalStringI);

我使用预先定义的表达式A = I * math.log10(I)-1.2和它作品,但是当我在文本框中输入相同的东西时,它不会。 我做了一些搜索,它提出了一些在运行时编译代码的方法。

任何想法如何做到这一点? 我是一个绝对的初学者。 感谢:)

+1

有没有在框架中任一公用事业你正在尝试做的,以评估任意表达式字符串。实际解析字符串并编写逻辑来执行评估会更好。正如你现在所做的那样,没有简单的方法去做你想做的事情。 –

+1

@JeffMercado:说“框架中没有东西”总是很危险,因为它很容易出错。碰巧你是。 –

回答

2

该问题在您的stringEvaluate StringBuilder中。当用“math.sin”替换“sin”时,stringEvaluate内的内容仍然是一个字符串。你有正确的想法,但你得到的错误是因为这个事实。

Math.sinMath类中的一种方法,因此无法像调用​​时那样对其进行操作。

这将是一个相当大的承诺实现你的目标,但我会去这样理解:

  1. 创建一个类(也许称之为表达式)。
  2. Expression类的成员可能包含操作符和操作数的列表,也可能是一个称为solution的双精度元素。
  3. 将此类传递给实例化的字符串,并使用StringBuilder类将其拆分。例如,如果遇到“罪”,将Math.sin添加到运算符集合(我将使用类型对象)。
  4. 上述字符串中的每个运算符和操作数应该放在两个集合中。
  5. 创建一个方法来相应地评估操作数和操作数集合中的元素。这可能会对超过2个操作员的复杂计算变得粘滞,因为您必须实施PEMDAS-esque算法来重新排序集合以服从操作顺序(从而实现正确的解决方案)。

希望这有助于:)

0

.Parse方法(Int.Parsedouble.Parse等)将采取一个字符串,如 “25” 或 “3.141”,并将其转换为匹配值类型(INT 25,或双3.141)。他们不会评估数学表达式!

您几乎必须编写自己的文本分析器和分析树评估器,或者探索运行时代码生成或MSIL代码发射。

Q & StackOverflow的格式答案都不在。

0

您可以使用该框架包含的用于JScript.NET代码的eval函数。

更多细节:http://odetocode.com/code/80.aspx

或者,如果你不害怕使用类标记为“过时”,它真的很容易:

static string EvalExpression(string s) 
{ 
    return Microsoft.JScript.Eval.JScriptEvaluate(s, null, Microsoft.JScript.Vsa.VsaEngine.CreateEngine()).ToString(); 
} 

例如,输入"Math.cos(Math.PI/3)"其结果是"0.5"(这是60度的正确余弦)