private void HandleConditional(PolishNotation element)
        {
            EnsureStackHeadNotIdentifier();
            decimal operand1 = Convert.ToDecimal(_stack.Pop());

            EnsureStackHeadNotIdentifier();
            decimal operand2 = Convert.ToDecimal(_stack.Pop());
            bool    result;

            switch (element.Token)
            {
            case "equals":
                result = decimal.Equals(operand2, operand1);
                break;

            case "greaterthn":
                result = operand2 > operand1;
                break;

            case "lessthn":
                result = operand2 < operand1;
                break;

            default:
                throw new ArgumentOutOfRangeException(nameof(element.Token), element.Token,
                                                      "Unknown conditional operator");
            }

            _stack.Push(result.ToString());
        }
        private void button1_Click(object sender, EventArgs e)
        {
            notation = new PolishNotation(txtExpresion.Text);
            notation.generateTree();
            preOrder = notation.getPreOrder();

            lblPreOrder.Text  = "PreOrder:   " + preOrder;
            lblPostOrder.Text = notation.getPostOrder();
            lblInOrder.Text   = notation.getInOrder();
        }
Esempio n. 3
0
    public void AnswerClick()
    {
        PolishNotation ob     = new PolishNotation();
        string         polska = ob.Transform(inPut.text);

        polish.text = polska;

        Calculator ob2 = new Calculator();
        int        res = ob2.Result(polska);

        answer.text = res.ToString();
    }
        private void HandleArithmeticUnary(PolishNotation element)
        {
            if (element.Token == "@+")
            {
                return;
            }

            // "-"
            EnsureStackHeadNotIdentifier();
            decimal operand1 = Convert.ToDecimal(_stack.Pop());

            _stack.Push((-operand1).ToString(CultureInfo.InvariantCulture));
        }
Esempio n. 5
0
        private void AddOperatorToStack(string @operator)
        {
            // Відкриваюча дужка "(" повинна мати найнижчий пріоритет, але записуватися в стек, нічого не виштовхуючи
            if (@operator == "(")
            {
                Stack.Push(new PolishNotation {
                    Token = @operator, Type = PolishNotationTokenType.Operator
                });
                return;
            }

            // 3.	Якщо стек порожній, то поточна операція заноситься в стек
            if (Stack.Count == 0)
            {
                Stack.Push(new PolishNotation {
                    Token = @operator, Type = PolishNotationTokenType.Operator
                });
                return;
            }

            PolishNotation head      = Stack.Peek();
            string         headToken = head.Token.StartsWith("if")
                                ? "if"
                                : head.Token.StartsWith("while")
                                        ? "while"
                                        : head.Token;

            // 2.	Якщо пріоритет операції, що знаходиться в стеку,
            //      не менший за пріоритет поточної вхідної операції,
            //      то операція зі стека подається на вихід і п.2 повторюється,
            if (_operatorsPriorities[headToken] >= _operatorsPriorities[@operator])
            {
                PolishNotation notation = Stack.Pop();
                if (notation.Token != "(")                 // Причому "(" ніколи не передається на вихід
                {
                    ReversePolishNotation.Add(notation);   // операція зі стека подається на вихід
                }

                AddOperatorToStack(@operator);                 // п.2 повторюється
                return;
            }

            // інакше поточна операція заноситься в стек.
            if (@operator != ")")             // Причому ")" ніколи не заноситься в стек
            {
                Stack.Push(new PolishNotation {
                    Token = @operator, Type = PolishNotationTokenType.Operator
                });
            }
        }
Esempio n. 6
0
        private String change(List <String> symbols, String idName, String conValue)
        {
            String result = builder.findAndChange(symbols);

            if (!result.Equals(" "))
            {
                if (compare(symbols, new Sentence("", "@выражение + @терм1").Tail))
                {
                    PolishNotation.Add(new PolishNotationElement("+", true));
                }
                else
                if (compare(symbols, new Sentence("", "@выражение - @терм1").Tail))
                {
                    PolishNotation.Add(new PolishNotationElement("-", true));
                }
                else
                if (compare(symbols, new Sentence("", "@терм * @множитель").Tail))
                {
                    PolishNotation.Add(new PolishNotationElement("*", true));
                }
                else
                if (compare(symbols, new Sentence("", "@терм / @множитель").Tail))
                {
                    PolishNotation.Add(new PolishNotationElement("/", true));
                }
                else
                if (compare(symbols, new Sentence("", "- @терм1").Tail))
                {
                    PolishNotation.Add(new PolishNotationElement("@", true));
                }
                else
                if (compare(symbols, new Sentence("", "id").Tail))
                {
                    PolishNotation.Add(new PolishNotationElement(idName, false, true));
                }
                else
                if (compare(symbols, new Sentence("", "const").Tail))
                {
                    PolishNotation.Add(new PolishNotationElement(conValue, false, false));
                }
            }
            return(result);
        }
        private void HandleArithmeticBinary(PolishNotation element)
        {
            EnsureStackHeadNotIdentifier();
            decimal operand1 = Convert.ToDecimal(_stack.Pop());

            EnsureStackHeadNotIdentifier();
            decimal operand2 = Convert.ToDecimal(_stack.Pop());
            decimal result;

            switch (element.Token)
            {
            case "+":
                result = operand2 + operand1;
                break;

            case "-":
                result = operand2 - operand1;
                break;

            case "*":
                result = operand2 * operand1;
                break;

            case "/":
                if (operand1 == 0)
                {
                    throw new RuntimeException("Division by 0");
                }
                result = operand2 / operand1;
                break;

            default:
                throw new ArgumentOutOfRangeException(nameof(element.Token), element.Token,
                                                      "Unknown binary arithmetic operator");
            }

            _stack.Push(result.ToString(CultureInfo.InvariantCulture));
        }
Esempio n. 8
0
 public void PolishNotationTests(string str, double expected)
 {
     Assert.AreEqual(PolishNotation.Calc(str), expected);
 }
        public ExecutionResult Run(
            PolishResult polishResult,
            ExecutionPoint executionPoint = default,
            decimal input = default)
        {
            var outputBuilder = new StringBuilder();

            _stack.Clear();
            _declaredIdentifiers.Clear();
            _identifiersValues.Clear();
            int i = 0;

            if (executionPoint != default)
            {
                _stack = executionPoint.Stack;
                _declaredIdentifiers = executionPoint.DeclaredIdentifiers;
                _identifiersValues   = executionPoint.IdentifiersValues;
                i = executionPoint.PolishNotationIndex;

                _stack.Push(input.ToString(CultureInfo.InvariantCulture));
                HandleSet();
            }

            try
            {
                while (i < polishResult.ReversePolishNotation.Count)
                {
                    PolishNotation element = polishResult.ReversePolishNotation[i];

                    switch (element.Type)
                    {
                    case PolishNotationTokenType.Identifier:
                        _stack.Push(_identifiersValues.ContainsKey(element.Token) &&
                                    !element.IsAssignmentToThisIdentifier
                                                                ? _identifiersValues[element.Token].ToString(CultureInfo.InvariantCulture)
                                                                : element.Token); // only for declaration or assignment
                        break;

                    case PolishNotationTokenType.Literal:
                        _stack.Push(element.Token);
                        break;

                    case PolishNotationTokenType.Operator:
                        switch (element.Token)
                        {
                        case "@+":
                        case "@-":
                            HandleArithmeticUnary(element);
                            break;

                        case "+":
                        case "-":
                        case "*":
                        case "/":
                            HandleArithmeticBinary(element);
                            break;

                        case "var":
                            HandleVar();
                            break;

                        case "set":
                            HandleSet();
                            break;

                        case "write":
                            string head = _stack.Pop();
                            if (head.StartsWith("@"))
                            {
                                throw new RuntimeException($"{head} is not declared");
                            }

                            outputBuilder.AppendLine(head.ToString(CultureInfo.InvariantCulture));
                            break;

                        case "read":
                            return(new ExecutionResult
                            {
                                Type = ExecutionResultType.InputRequired,
                                Output = outputBuilder.ToString(),
                                ExecutionPoint = new ExecutionPoint
                                {
                                    PolishNotationIndex = i + 1,
                                    Stack = _stack,
                                    DeclaredIdentifiers = _declaredIdentifiers,
                                    IdentifiersValues = _identifiersValues,
                                    PolishResult = polishResult
                                }
                            });

                        case "equals":
                        case "greaterthn":
                        case "lessthn":
                            HandleConditional(element);
                            break;
                        }
                        break;

                    case PolishNotationTokenType.Delimiter:
                        break;

                    case PolishNotationTokenType.If:
                        break;

                    case PolishNotationTokenType.Then:
                        break;

                    case PolishNotationTokenType.Fi:
                        break;

                    case PolishNotationTokenType.While:
                        break;

                    case PolishNotationTokenType.TechnicalDo:
                        break;

                    case PolishNotationTokenType.Enddo:
                        break;

                    case PolishNotationTokenType.Label:
                        PolishNotation nextElement = polishResult.ReversePolishNotation[i + 1];
                        switch (nextElement.Token)
                        {
                        case "УПХ":
                            bool operand = Convert.ToBoolean(_stack.Pop());
                            if (!operand)
                            {
                                i = polishResult.LabelAddresses[element.Token];
                                continue;
                            }

                            break;

                        case "БП":
                            i = polishResult.LabelAddresses[element.Token];
                            continue;
                        }
                        break;

                    default:
                        throw new ArgumentOutOfRangeException();
                    }

                    i++;
                }
            }
            catch (RuntimeException e)
            {
                outputBuilder.AppendLine(e.Message);
            }

            return(new ExecutionResult
            {
                Type = ExecutionResultType.Completed,
                Output = outputBuilder.ToString()
            });
        }
Esempio n. 10
0
        private void DijkstraStep(string input, PolishNotationTokenType type, bool isAssignmentToThisIdentifier = false)
        {
            switch (type)
            {
            // 1.	Ідентифікатори та константи проходять від входу прямо до виходу
            case PolishNotationTokenType.Identifier:
            case PolishNotationTokenType.Literal:
                ReversePolishNotation.Add(new PolishNotation
                {
                    Token = input, Type = type, IsAssignmentToThisIdentifier = isAssignmentToThisIdentifier
                });
                break;

            // Операції звичайно потрапляють на вихід через магазин
            case PolishNotationTokenType.Operator:
                AddOperatorToStack(input);
                break;

            // 4.	Якщо вхідний ланцюжок порожній, всі операції зі стека по черзі передаються на вихід
            //      за ознакою кінця виразу (наприклад, ";").
            case PolishNotationTokenType.Delimiter:
            {
                while (Stack.Count != 0 &&
                       !Stack.Peek().Token.StartsWith("if") &&
                       !Stack.Peek().Token.StartsWith("while"))
                {
                    ReversePolishNotation.Add(Stack.Pop());
                }

//					ReversePolishNotation.Add(new PolishNotation {Token = input, Type = type});
            }
            break;

            case PolishNotationTokenType.If:
                Stack.Push(new PolishNotation {
                    Token = input, Type = type
                });
                break;

            // Символ then з пріоритетом 1 виштовхує зі стека всі знаки до першого
            // if виключно. При цьому генерується нова мітка mi й у вихідний рядок
            // заноситься mi УПХ. Потім мітка mi заноситься в таблицю міток і дописується у вершину стека,
            // таким чином, запис if у вершині стека перетворюється на запис if mi
            case PolishNotationTokenType.Then:
            {
                PolishNotation head = Stack.Peek();
                while (!head.Token.StartsWith("if"))
                {
                    ReversePolishNotation.Add(Stack.Pop());
                    head = Stack.Peek();
                }

                string label = GenerateLabel();
                head.Token = $"{head.Token} {label}";
                ReversePolishNotation.Add(new PolishNotation
                    {
                        Token = $"{label}", Type = PolishNotationTokenType.Label
                    });
                ReversePolishNotation.Add(new PolishNotation {
                        Token = "УПХ", Type = type
                    });
            }
            break;

            // Символ кінця умовного оператора (наприклад, ; або end) виштовхує зі
            // стека все до найближчого if. Це може бути if mi mi+1 (або if mi у разі
            // конструкції if <вираз> then <оператор>;). Запис видаляється зі стека,
            // а у вихідний рядок додається mi+1: (або mi: у випадку неповного оператора умовного переходу).
            case PolishNotationTokenType.Fi:
            {
                PolishNotation head = Stack.Peek();
                while (!head.Token.StartsWith("if"))
                {
                    ReversePolishNotation.Add(Stack.Pop());
                    head = Stack.Peek();
                }

                head = Stack.Pop();
                string label = head.Token.Split(" ").Last();
                ReversePolishNotation.Add(new PolishNotation
                    {
                        Token = $"{label}", Type = PolishNotationTokenType.Label
                    });
                ReversePolishNotation.Add(new PolishNotation {
                        Token = ":", Type = type
                    });
                _labelAddresses[label] = ReversePolishNotation.Count;
            }
            break;

            case PolishNotationTokenType.While:
            {
                string label = GenerateLabel();
                Stack.Push(new PolishNotation {
                        Token = $"{input} {label}", Type = type
                    });
                ReversePolishNotation.Add(new PolishNotation
                    {
                        Token = $"{label}", Type = PolishNotationTokenType.Label
                    });
                ReversePolishNotation.Add(new PolishNotation {
                        Token = $":", Type = type
                    });
                _labelAddresses[label] = ReversePolishNotation.Count;
            }
            break;

            case PolishNotationTokenType.TechnicalDo:
            {
                PolishNotation head = Stack.Peek();
                while (!head.Token.StartsWith("while"))
                {
                    ReversePolishNotation.Add(Stack.Pop());
                    head = Stack.Peek();
                }

                string label = GenerateLabel();
                head.Token = $"{head.Token} {label}";
                ReversePolishNotation.Add(new PolishNotation
                    {
                        Token = $"{label}", Type = PolishNotationTokenType.Label
                    });
                ReversePolishNotation.Add(new PolishNotation {
                        Token = "УПХ", Type = type
                    });
            }
            break;

            case PolishNotationTokenType.Enddo:
            {
                PolishNotation head = Stack.Peek();
                while (!head.Token.StartsWith("while"))
                {
                    ReversePolishNotation.Add(Stack.Pop());
                    head = Stack.Peek();
                }

                head = Stack.Pop();
                string[] labels = head.Token.Split(" ");
                ReversePolishNotation.Add(new PolishNotation
                    {
                        Token = $"{labels[1]}", Type = PolishNotationTokenType.Label
                    });
                ReversePolishNotation.Add(new PolishNotation {
                        Token = "БП", Type = type
                    });
                ReversePolishNotation.Add(new PolishNotation
                    {
                        Token = $"{labels.Last()}", Type = PolishNotationTokenType.Label
                    });
                ReversePolishNotation.Add(new PolishNotation {
                        Token = $":", Type = type
                    });
                _labelAddresses[labels.Last()] = ReversePolishNotation.Count;
            }
            break;

            default:
                throw new ArgumentOutOfRangeException(nameof(type), type, null);
            }

            Trace.Add(new PolishTrace
            {
                Input = input,
//				Stack = new Stack<PolishNotation>(Stack),
                Stack = Stack.Clone(),
                ReversePolishNotation = new List <PolishNotation>(ReversePolishNotation)
            });
            MoveNext();
        }