Ejemplo n.º 1
0
        private void OnClosingBracket()
        {
            var funcNode = new MultiTreeNode <Value>(new Value(ValueType.Function, null));

            while (OperationsStack.Peek() != "(")
            {
                if (EvalOperator() == ",")
                {
                    funcNode.AddChild(OperandsStack.Pop());
                }
            }

            OperationsStack.Pop();

            if (OperationsStack.Count > 0 && Library.IsFunction(OperationsStack.Peek()))
            {
                funcNode.Data.Val = OperationsStack.Pop();
                OperandsStack.Push(funcNode);
                return;
            }

            if (funcNode.Count > 0)
            {
                funcNode.Data.Val = "MkTuple";
                OperandsStack.Push(funcNode);
            }
        }
Ejemplo n.º 2
0
        private void OnClosingSquareBracket()
        {
            var funcNode = new MultiTreeNode <Value>(new Value(ValueType.Function, null));

            while (OperationsStack.Peek() != "[")
            {
                if (EvalOperator() == ",")
                {
                    funcNode.AddChild(OperandsStack.Pop());
                }
            }

            OperationsStack.Pop();

            if (OperationsStack.Count > 0 && OperationsStack.Peek() == "MkList")
            {
                funcNode.Data.Val = OperationsStack.Pop();
                OperandsStack.Push(funcNode);
                return;
            }

            if (OperationsStack.Count > 0 && OperationsStack.Peek() == "ByIdx")
            {
                funcNode.Data.Val = OperationsStack.Pop();
                funcNode.AddChild(OperandsStack.Pop());
                funcNode.AddChild(OperandsStack.Pop());
                OperandsStack.Push(funcNode);
                return;
            }
        }
Ejemplo n.º 3
0
 private void OnFunction(TokenLine.TokenEnum token)
 {
     if (token.PeekNext() == "(")
     {
         OperationsStack.Push(token.Current);
         OperationsStack.Push("(");
         token.MoveNext();
         if (token.PeekNext() != ")")
         {
             OperationsStack.Push(",");
         }
     }
     else
     {
         OperandsStack.Push(new MultiTreeNode <Value>(new Value(ValueType.Variable, token.Current)));
     }
 }
Ejemplo n.º 4
0
        private void ParseToken(TokenLine.TokenEnum token)
        {
            if (Library.IsFunction(token.Current))
            {
                OnFunction(token);
            }

            else if (token.Current == "[")
            {
                OnOpeningSquareBracket(token);
            }

            else if (RouteOperators.Contains(token.Current))
            {
                OperationsStack.Push(token.Current);
            }

            else if (token.Current == ")")
            {
                OnClosingBracket();
            }

            else if (token.Current == "]")
            {
                OnClosingSquareBracket();
            }

            else if (Library.IsOperator(token.Current))
            {
                while (OperationsStack.Count > 0 && Library.Operators[OperationsStack.Peek()] >= Library.Operators[token.Current])
                {
                    EvalOperator();
                }

                OperationsStack.Push(token.Current);
            }

            else
            {
                var value = Translator.ParseTypes(token.Current);
                OperandsStack.Push(value == null
                    ? new MultiTreeNode <Value>(new Value(ValueType.Variable, token.Current))
                    : new MultiTreeNode <Value>(new Value(ValueType.Value, value)));
            }
        }
Ejemplo n.º 5
0
 private void OnOpeningSquareBracket(TokenLine.TokenEnum token)
 {
     if (token.PeekPrev() == null || token.PeekPrev() == "(" || token.PeekPrev() == "[" ||
         Library.Operators.ContainsKey(token.PeekPrev()))
     {
         OperationsStack.Push("MkList");
         OperationsStack.Push("[");
         if (token.PeekNext() != "]")
         {
             OperationsStack.Push(",");
         }
     }
     else
     {
         OperationsStack.Push("ByIdx");
         OperationsStack.Push("[");
     }
 }
Ejemplo n.º 6
0
        public MultiTreeNode <Value> ParseLine(string line)
        {
            var currentToken = new TokenLine(line).GetEnumerator();

            while (currentToken.MoveNext())
            {
                ParseToken(currentToken);
            }

            while (OperationsStack.Count != 0)
            {
                EvalOperator();
            }

            var result = OperandsStack.Pop();

            OperationsStack.Clear();
            OperandsStack.Clear();
            return(result);
        }
Ejemplo n.º 7
0
        private string EvalOperator()
        {
            var op = OperationsStack.Pop();

            if (op == ",")
            {
                return(op);
            }

            if (!Library.Operators.ContainsKey(op))
            {
                throw new ArgumentException($"Expected operator, but was <{op}>");
            }

            var opNode = new MultiTreeNode <Value>(new Value(ValueType.Function, op));

            opNode.AddChild(OperandsStack.Pop());
            opNode.AddChild(OperandsStack.Pop());
            OperandsStack.Push(opNode);
            return(op);
        }
Ejemplo n.º 8
0
        /// <summary>
        /// Returns a compiled expression for specified source string.
        /// </summary>
        public CompiledExpression Compile(PreparedExpression preparedExpression)
        {
            if (preparedExpression == null)
            {
                throw new ArgumentNullException("preparedExpression");
            }
            //
            OperationsStack operationsStack = new OperationsStack(operationsRegistry);

            //
            for (int itemIndex = 0; itemIndex < preparedExpression.PreparedExpressionItems.Count; itemIndex++)
            {
                PreparedExpressionItem item = preparedExpression.PreparedExpressionItems[itemIndex];
                // If constant or variable - add to result
                if (item.Kind == PreparedExpressionItemKind.Constant)
                {
                    operationsStack.PushConstant(item.Constant);
                }
                if (item.Kind == PreparedExpressionItemKind.Variable)
                {
                    operationsStack.PushVariable(item.VariableName);
                }
                // If delimiter
                if (item.Kind == PreparedExpressionItemKind.Delimiter)
                {
                    operationsStack.PushDelimiter(item.DelimiterKind);
                }
                // Signature (operator signature / part of signature / function)
                if (item.Kind == PreparedExpressionItemKind.Signature)
                {
                    List <Operation> operations = new List <Operation>(operationsRegistry.GetOperationsUsingSignature(item.Signature));
                    operations.Sort(new Comparison <Operation>(compareOperationsByOperandsCount));
                    //
                    for (int i = 0; i < operations.Count; i++)
                    {
                        Operation operation = operations[i];
                        // Operator
                        if (operation.Kind == OperationKind.Operator)
                        {
                            // Unary operator
                            if (operation.OperandsCount == 1)
                            {
                                // If operator placed at the start of subexpression
                                if ((itemIndex == 0) ||
                                    ((itemIndex > 0) && (preparedExpression.PreparedExpressionItems[itemIndex - 1].Kind == PreparedExpressionItemKind.Delimiter) && (preparedExpression.PreparedExpressionItems[itemIndex - 1].DelimiterKind == DelimiterKind.OpeningBrace) || (preparedExpression.PreparedExpressionItems[itemIndex - 1].DelimiterKind == DelimiterKind.Comma)))
                                {
                                    //
                                    operationsStack.PushUnaryOperator(operation);
                                    break;
                                }
                            }
                            // Binary operator
                            if (operation.OperandsCount == 2)
                            {
                                operationsStack.PushBinaryOperator(operation);
                                break;
                            }
                            // Ternary and more
                            if (operation.OperandsCount > 2)
                            {
                                int partNumber = 0;
                                for (int k = 0; k < operation.Signature.Length; k++)
                                {
                                    if (operation.Signature[k] == item.Signature)
                                    {
                                        partNumber = k + 1;
                                        break;
                                    }
                                }
                                // If it is start part in signature
                                if (partNumber == 1)
                                {
                                    operationsStack.PushComplexOperatorFirstSignature(operation);
                                    break;
                                }
                                //
                                operationsStack.PushComplexOperatorNonFirstSignature(operation, partNumber);
                                break;
                            }
                        }
                        // Function
                        if (operation.Kind == OperationKind.Function)
                        {
                            operationsStack.PushFunction(operation);
                            break;
                        }
                    }
                }
            }
            //
            operationsStack.DoFinalFlush();
            //
            CompiledExpression res = operationsStack.GetResult();

            if (!isCompiledExpressionStackBalanced(res))
            {
                throw new CompilerSyntaxException("Operands disbalance detected.");
            }
            return(res);
        }
Ejemplo n.º 9
0
 /// <summary>
 /// Returns a compiled expression for specified source string.
 /// </summary>
 public CompiledExpression Compile(PreparedExpression preparedExpression) {
     if (preparedExpression == null)
         throw new ArgumentNullException("preparedExpression");
     //
     OperationsStack operationsStack = new OperationsStack(operationsRegistry);
     //
     for (int itemIndex = 0; itemIndex < preparedExpression.PreparedExpressionItems.Count; itemIndex++) {
         PreparedExpressionItem item = preparedExpression.PreparedExpressionItems[itemIndex];
         // If constant or variable - add to result
         if (item.Kind == PreparedExpressionItemKind.Constant)
             operationsStack.PushConstant(item.Constant);
         if (item.Kind == PreparedExpressionItemKind.Variable)
             operationsStack.PushVariable(item.VariableName);
         // If delimiter
         if (item.Kind == PreparedExpressionItemKind.Delimiter) {
             operationsStack.PushDelimiter(item.DelimiterKind);
         }
         // Signature (operator signature / part of signature / function)
         if (item.Kind == PreparedExpressionItemKind.Signature) {
             List<Operation> operations = new List<Operation>(operationsRegistry.GetOperationsUsingSignature(item.Signature));
             operations.Sort(new Comparison<Operation>(compareOperationsByOperandsCount));
             //
             for (int i = 0; i < operations.Count; i++) {
                 Operation operation = operations[i];
                 // Operator
                 if (operation.Kind == OperationKind.Operator) {
                     // Unary operator
                     if (operation.OperandsCount == 1) {
                         // If operator placed at the start of subexpression
                         if ((itemIndex == 0) ||
                             ((itemIndex > 0) && (preparedExpression.PreparedExpressionItems[itemIndex - 1].Kind == PreparedExpressionItemKind.Delimiter) && (preparedExpression.PreparedExpressionItems[itemIndex - 1].DelimiterKind == DelimiterKind.OpeningBrace)|| (preparedExpression.PreparedExpressionItems[itemIndex-1].DelimiterKind == DelimiterKind.Comma))) {
                             //
                             operationsStack.PushUnaryOperator(operation);
                             break;
                         }
                     }
                     // Binary operator
                     if (operation.OperandsCount == 2) {
                         operationsStack.PushBinaryOperator(operation);
                         break;
                     }
                     // Ternary and more
                     if (operation.OperandsCount > 2) {
                         int partNumber = 0;
                         for (int k = 0; k < operation.Signature.Length; k++) {
                             if (operation.Signature[k] == item.Signature) {
                                 partNumber = k + 1;
                                 break;
                             }
                         }
                         // If it is start part in signature
                         if (partNumber == 1) {
                             operationsStack.PushComplexOperatorFirstSignature(operation);
                             break;
                         }
                         //
                         operationsStack.PushComplexOperatorNonFirstSignature(operation, partNumber);
                         break;
                     }
                 }
                 // Function
                 if (operation.Kind == OperationKind.Function) {
                     operationsStack.PushFunction(operation);
                     break;
                 }
             }
         }
     }
     // 
     operationsStack.DoFinalFlush();
     //
     CompiledExpression res = operationsStack.GetResult();
     if (!isCompiledExpressionStackBalanced(res))
         throw new CompilerSyntaxException("Operands disbalance detected.");
     return res;
 }