Beispiel #1
0
        public static double Simulate(List <string> pass3, double[] args)
        {
            var           list = InfixToAstParser.ShuntingYardAlgorithm(string.Join("", pass3));
            string        patternToFindLetters = @"[a-z]+$";
            List <string> tokens = new List <string>();

            foreach (var element in list)
            {
                if (element == "sin" || element == "cos" || element == "ctn" || element == "tan" || element == "log" || element == "ex")
                {
                    tokens.Add(element.ToString());
                    continue;
                }
                if (Regex.IsMatch(element.ToString(), patternToFindLetters))
                {
                    double value = args[InfixToAstParser.ExpressionArgs.IndexOf(element.ToString())];
                    tokens.Add(value.ToString());
                }
                else
                {
                    tokens.Add(element.ToString());
                    continue;
                }
            }
            Stack <double> resultStack = new Stack <double>();

            foreach (var token in tokens)
            {
                double leftOperand;
                double rightOperand;
                if (InfixToAstParser.IsNumber(token.ToString()))
                {
                    resultStack.Push(double.Parse(token.ToString()));
                }
                switch (token)
                {
                case "+":
                    resultStack.Push(resultStack.Pop() + resultStack.Pop());
                    break;

                case "-":
                    rightOperand = resultStack.Pop();
                    resultStack.Push(resultStack.Pop() - rightOperand);
                    break;

                case "*":
                    resultStack.Push(resultStack.Pop() * resultStack.Pop());
                    break;

                case "/":
                    rightOperand = resultStack.Pop();
                    leftOperand  = resultStack.Pop();
                    resultStack.Push(leftOperand / rightOperand);
                    break;

                case "^":
                    rightOperand = resultStack.Pop();
                    leftOperand  = resultStack.Pop();
                    resultStack.Push(Math.Pow(leftOperand, rightOperand));
                    break;

                case "sin":
                    double numberToSin = resultStack.Pop();
                    resultStack.Push(Math.Sin(numberToSin));
                    break;

                case "cos":
                    double numberToCos = resultStack.Pop();
                    resultStack.Push(Math.Cos(numberToCos));
                    break;

                case "ctn":
                    double numberToCtn = resultStack.Pop();
                    resultStack.Push(1 / Math.Tan(numberToCtn));
                    break;

                case "tan":
                    double numberToTan = resultStack.Pop();
                    resultStack.Push(Math.Tan(numberToTan));
                    break;

                case "log":
                    double numberToLog = resultStack.Pop();
                    resultStack.Push(Math.Log(numberToLog));
                    break;

                case "ex":
                    double numberToEx = resultStack.Pop();
                    resultStack.Push(Math.Exp(numberToEx));
                    break;
                }
            }
            var result = resultStack.Pop();

            return(result);
        }
Beispiel #2
0
 public List <string> ThirdPass(AbstractSyntaxTree tree)
 {
     Simulator.Postfix.Clear();
     Simulator.NodesToPolishNotation(tree);
     return(InfixToAstParser.PostfixToInfix(Simulator.Postfix).Select(x => Convert.ToString(x)).ToList());
 }
Beispiel #3
0
        public AbstractSyntaxTree SecondPass(AbstractSyntaxTree tree)
        {
            Simulator.Postfix.Clear();
            Simulator.NodesToPolishNotation(tree);
            var           tokens = InfixToAstParser.ShuntingYardAlgorithm(InfixToAstParser.PostfixToInfix(Simulator.Postfix));
            List <string> result = new List <string>();

            foreach (var token in tokens)
            {
                if (Regex.IsMatch(token, @"cos|sin|tan|ctn|log|ex"))
                {
                    string operand = result[result.Count - 1];
                    if (!Regex.IsMatch(operand.ToString(), @"[0-9]+$") || operand == "cos" || operand == "sin" || operand == "tan" || operand == "ctn" || operand == "log" || operand == "ex")
                    {
                        result.Add(token);
                        continue;
                    }
                    result.RemoveAt(result.Count - 1);
                    switch (token)
                    {
                    case "sin":
                        result.Add(Convert.ToString(Math.Sin(Convert.ToDouble(operand))));
                        break;

                    case "cos":
                        result.Add(Convert.ToString(Math.Cos(Convert.ToDouble(operand))));
                        break;

                    case "ctn":
                        result.Add(Convert.ToString(1 / Math.Tan(Convert.ToDouble(operand))));
                        break;

                    case "tan":
                        result.Add(Convert.ToString(Math.Tan(Convert.ToDouble(operand))));
                        break;

                    case "log":
                        result.Add(Convert.ToString(Math.Log(Convert.ToDouble(operand))));
                        break;

                    case "ex":
                        result.Add(Convert.ToString(Math.Exp(Convert.ToDouble(operand))));
                        break;
                    }
                }
                const string pattern = @"[a-z]+|[0-9]+$";
                if (Regex.IsMatch(token.ToString(), pattern))
                {
                    result.Add(token.ToString());
                    continue;
                }
                string rightOperand = result[result.Count - 1];
                string leftOperand  = result[result.Count - 2];
                if (!Regex.IsMatch(rightOperand.ToString(), @"[0-9]+$") || !Regex.IsMatch(leftOperand.ToString(), @"[0-9]+$"))
                {
                    result.Add(token);
                    continue;
                }
                result.RemoveAt(result.Count - 1);
                result.RemoveAt(result.Count - 1);
                switch (token)
                {
                case "+":
                    result.Add(Convert.ToString(Convert.ToDouble(leftOperand) + Convert.ToDouble(rightOperand)));
                    break;

                case "-":
                    result.Add(Convert.ToString(Convert.ToDouble(leftOperand) - Convert.ToDouble(rightOperand)));
                    break;

                case "*":
                    result.Add(Convert.ToString(Convert.ToDouble(leftOperand) * Convert.ToDouble(rightOperand)));
                    break;

                case "/":
                    result.Add(Convert.ToString(Convert.ToDouble(leftOperand) / Convert.ToDouble(rightOperand)));
                    break;

                case "^":
                    result.Add(Convert.ToString(Math.Pow(Convert.ToDouble(leftOperand), Convert.ToDouble(rightOperand))));
                    break;
                }
            }
            return(InfixToAstParser.Parse(InfixToAstParser.PostfixToInfix(result)));
        }
Beispiel #4
0
 public AbstractSyntaxTree FirstPass(string expression)
 {
     return(InfixToAstParser.BuildTree(expression));
 }