public override bool Equals(object obj) { EvalValue b = obj as EvalValue; if (stringValue == null) { return(D == b.D); } else { return(S == b.S); } }
private decimal evalExternalFunctionCall(String funcName, String expr) { Tokenizer paramTokenizer = new Tokenizer(expr, ",", true); System.Collections.ArrayList functionParms = System.Collections.ArrayList.Synchronized(new System.Collections.ArrayList(10)); while (paramTokenizer.HasMoreTokens()) { String arg = getNextToken(paramTokenizer).Trim(); if ((arg.StartsWith("\"") || arg.StartsWith("'")) && (arg.EndsWith("\"") || arg.EndsWith("'"))) { // it is a string functionParms.Add(arg.Substring(1, (arg.Length - 1) - (1))); } else { // evaluate the parameter EvalValue eValue = eval(arg); // The corresponding type of parameter is passed if (eValue.S == null) { functionParms.Add(eValue.D); } else { functionParms.Add(eValue.S); } } if (paramTokenizer.HasMoreTokens()) { // Consume the ',' paramTokenizer.NextToken(); } } functionParms.Add((decimal)0); System.Object[] callParms = new System.Object[functionParms.Count]; functionParms.CopyTo(callParms); bool pAdded = false; try { funcName = funcName.ToLower(); DynamicExecute(funcName, callParms); } catch (System.Exception e) { bool retrySuccessful = false; if (!pAdded && e.ToString().IndexOf("ClassNotFoundException") != -1) { try { DynamicExecute("p" + funcName, callParms); retrySuccessful = true; } catch (System.Exception) { } } if (!retrySuccessful) { return(throwException(EXTERNAL_FUNCTION_ERROR, e.Message)); } } return(Convert.ToDecimal(callParms[callParms.Length - 1], System.Globalization.CultureInfo.InvariantCulture)); }
private decimal evalFuncCall(String funcName, String expr) { EvalValue result = 0; if (funcName.ToUpper().Equals("rnd".ToUpper())) { // random function result = (decimal)NumberUtil.Random(); } else // single variable function if (funcName.ToUpper().Equals("abs".ToUpper())) { result = System.Math.Abs(eval(expr).D); } else if (funcName.ToUpper().Equals("int".ToUpper())) { result = System.Math.Floor(eval(expr).D); } else if (funcName.ToUpper().Equals("frac".ToUpper())) { EvalValue value = eval(expr); EvalValue int_part = System.Math.Floor(value.D); result = value - int_part; } else if (funcName.ToUpper().Equals("sin".ToUpper())) { result = (decimal)System.Math.Sin(Convert.ToDouble((decimal)eval(expr))); } else if (funcName.ToUpper().Equals("asin".ToUpper())) { result = (decimal)System.Math.Asin(Convert.ToDouble((decimal)eval(expr))); } else if (funcName.ToUpper().Equals("cos".ToUpper())) { result = (decimal)System.Math.Cos(Convert.ToDouble((decimal)eval(expr))); } else if (funcName.ToUpper().Equals("acos".ToUpper())) { decimal x = eval(expr).D; if (x > 1 || x < -1) { throwException(EVALUATION_ERROR, "Invalid range"); } result = (decimal)System.Math.Acos(Convert.ToDouble(x)); } else if (funcName.ToUpper().Equals("tan".ToUpper())) { result = (decimal)System.Math.Tan(Convert.ToDouble((decimal)eval(expr))); } else if (funcName.ToUpper().Equals("atan".ToUpper())) { result = (decimal)System.Math.Atan(Convert.ToDouble((decimal)eval(expr))); } else if (funcName.ToUpper().Equals("floor".ToUpper())) { result = (decimal)System.Math.Floor(Convert.ToDouble((decimal)eval(expr))); } else if (funcName.ToUpper().Equals("round".ToUpper())) { result = System.Math.Round(eval(expr)); } else if (funcName.ToUpper().Equals("ln".ToUpper()) || funcName.ToUpper().Equals("log".ToUpper())) { decimal val = eval(expr); if (val <= 0) { return(throwException(EVALUATION_ERROR, "Illegal argument (" + val + ") to function log(" + expr + ")")); } result = (decimal)System.Math.Log(Convert.ToDouble(val)); } else if (funcName.ToUpper().Equals("exp".ToUpper())) { result = (decimal)System.Math.Exp(Convert.ToDouble((decimal)eval(expr))); } else if (funcName.ToUpper().Equals("sqrt".ToUpper())) { result = (decimal)System.Math.Sqrt(Convert.ToDouble((decimal)eval(expr))); } else // internal functions of 2 variables if (funcName.ToUpper().Equals("pow".ToUpper()) || funcName.ToUpper().Equals("max".ToUpper()) || funcName.ToUpper().Equals("min".ToUpper())) { Tokenizer paramTokenizer = new Tokenizer(expr, ",", true); String sarg1, sarg2; try { sarg1 = getNextToken(paramTokenizer); paramTokenizer.NextToken(); sarg2 = getNextToken(paramTokenizer); } catch (System.ArgumentOutOfRangeException) { return(throwException(EVALUATION_ERROR, "The function " + funcName + " needs 2 arguments")); } decimal arg1 = eval(sarg1); decimal arg2 = eval(sarg2); if (funcName.ToUpper().Equals("pow".ToUpper())) { result = (decimal)System.Math.Pow(Convert.ToDouble(arg1), Convert.ToDouble(arg2)); } else if (funcName.ToUpper().Equals("max".ToUpper())) { result = System.Math.Max(arg1, arg2); } else if (funcName.ToUpper().Equals("min".ToUpper())) { result = System.Math.Min(arg1, arg2); } } else if (funcName.ToUpper().Equals("iif".ToUpper())) { // iif Tokenizer paramTokenizer = new Tokenizer(expr, ",", true); String sarg1, sarg2, sarg3; try { sarg1 = getNextToken(paramTokenizer); paramTokenizer.NextToken(); sarg2 = getNextToken(paramTokenizer); paramTokenizer.NextToken(); sarg3 = getNextToken(paramTokenizer); } catch (System.ArgumentOutOfRangeException) { return(throwException(EVALUATION_ERROR, "The function " + funcName + " needs 3 arguments")); } iifContext = true; bool iif_result = (eval(sarg1) != 0); iifContext = false; if (ErrCode != 0) { return(result); } if (iif_result) { result = eval(sarg2); } else { result = eval(sarg3); } } else { result = evalExternalFunctionCall(funcName, expr); } return(result); }
private EvalValue evaluate(String fullExpression, Tokenizer tokenizer, bool stopOnLowPrecedence) { EvalValue retVal = eval(tokenizer); EvalValue termino = 0; while (tokenizer.HasMoreTokens()) { if (stopOnLowPrecedence) { string nextOp; if (tokenizer.Peek(out nextOp) && nextOp.Length >= 1 && (nextOp[0] == '+' || nextOp[0] == '-')) { break; } } string soperador = tokenizer.NextToken(); if (String.IsNullOrEmpty(soperador.Trim())) { continue; } char operador = soperador[0]; switch (operador) { case '+': termino = evaluate(fullExpression, tokenizer, true); retVal = retVal + termino; break; case '-': termino = evaluate(fullExpression, tokenizer, true); retVal = retVal - termino; break; case '*': termino = eval(tokenizer); retVal = retVal * termino; break; case '/': termino = eval(tokenizer); if (termino == 0 && errCode == 0) { throwException(EVALUATION_ERROR, "Division by zero"); } if (errCode == 0) { retVal = retVal / termino; } break; case '>': return(retVal > evaluate(fullExpression, tokenizer) ? 1 : 0); case '<': return(retVal < evaluate(fullExpression, tokenizer) ? 1 : 0); case '=': return(retVal == evaluate(fullExpression, tokenizer) ? 1 : 0); case GE: return(retVal >= evaluate(fullExpression, tokenizer) ? 1 : 0); case LE: return(retVal <= evaluate(fullExpression, tokenizer) ? 1 : 0); case AND: return((retVal != 0) && (evaluate(fullExpression, tokenizer) != 0) ? 1 : 0); case OR: return((retVal != 0) || (evaluate(fullExpression, tokenizer) != 0) ? 1 : 0); case NE: return(retVal != evaluate(fullExpression, tokenizer) ? 1 : 0); default: throwException(EVALUATION_ERROR, "Unknown operator '" + soperador + "' found in expression '" + fullExpression + "'"); break; } } return(retVal); }