public ExpressinPosition(int index, int length)
 {
     this.Index = index;
     this.Length = length;
     this.Parameter = -1;
     this.Part = ExpressionPart.Text;
 }
示例#2
0
        private INode YieldExpression(ExpressionPart expressionPart)
        {
            if (expressionPart == null)
            {
                return(null);
            }
            var node = new ExpressionNode(expressionPart);

            return(node);
        }
示例#3
0
 public ExpressionNode(ExpressionPart expressionPart) : this(expressionPart.Expression)
 {
 }
示例#4
0
        /// <summary>
        /// Creates elements of the expression parts and checks.
        /// </summary>
        /// <param name="s">ExpressionString whose bracketed parts are parsed.</param>
        /// <returns>True if partsyntax was correct.</returns>
        private bool ParseExpressionPart(string s)
        {
            bool readVal = true; // true - reading values and unary operations; false - reading binary operations

            // adding a part
            ExpressionPart part = new ExpressionPart();
            part.expression = s;

            for (int i = 0; i < s.Length; i++)
            {
                SkipSpaces(s, ref i);
                if (i >= s.Length)
                    break;

                // reading element
                Element element = new Element(ref _floatingFormat);
                if (readVal)
                {
                    if (!ReadValue(s, ref i, element)) return false;
                }
                else
                {
                    if (!ReadOperation(s, ref i, element)) return false;
                }

                // saving element
                part.elements.Add(element);

                //in case operation was unary the next element should be value as well
                if (element.operation != tkOperation.operNOT && element.operation != tkOperation.operChangeSign)
                    readVal = !readVal;
            }

            if (part.elements.Count > 0)
            {
                _parts.Add(part);
                return true;
            }
            return false;
        }
示例#5
0
        /// <summary>Gets the ExpressionValue of the element of the given part.
        /// </summary>
        /// <param name="part">Part that contains the element.</param>
        /// <param name="elementId">Id of the element whose value is returned.</param>
        /// <returns>Value of the element.</returns>
        private ExpressionValue GetValue(ExpressionPart part, int elementId)
        {
            Element element = part.elements[elementId];

            if (element.wasCalculated)
                return element.calcVal;
            else if (element.partIndex != -1)
                return _parts[element.partIndex].val;
            else
                return element.val;
        }
示例#6
0
        /// <summary>
        /// Seeks operation with the highest priority and operands.
        /// </summary>
        /// <param name="part"></param>
        /// <param name="operation"></param>
        /// <returns></returns>
        private bool FindOperation(ExpressionPart part, Operation operation)
        {
            // seeking operation
            bool found = false;
            int priority = 255;

            List<Element> elements = part.elements;
            int size = elements.Count;
            for (int i = 0; i < size; i++)
            {
                Element element = elements[i];
                if (!element.turnedOff)
                {
                    if (element.type == tkElementType.etOperation)
                    {
                        if (element.priority < priority)
                        {
                            found = true;
                            priority = element.priority;
                            operation.id = i;
                        }
                    }
                }
            }
            if (!found)
            {
                _errorMessage = SymbologyMessageStrings.Expression_OperationNotFound;
                return false;
            }

            // seeking right operand
            operation.left = operation.right = -1;
            for (int i = operation.id + 1; i < size; i++)
            {
                Element element = elements[i];
                if (!element.turnedOff)
                {
                    if (element.type == tkElementType.etOperation)
                    {
                        if (element.operation != tkOperation.operNOT && element.operation != tkOperation.operChangeSign)
                        {
                            _errorMessage = SymbologyMessageStrings.Expression_OpereratorInsteadOfValue;
                            return false;
                        }
                    }
                    else
                    {
                        operation.right = i;
                        break;
                    }
                }
            }
            if (operation.right == -1)
            {
                _errorMessage = SymbologyMessageStrings.Expression_RightOperandMissing;
                return false;
            }

            // if the operator is binary, seeking left operand
            if (elements[operation.id].operation != tkOperation.operNOT && elements[operation.id].operation != tkOperation.operChangeSign)
            {
                for (int i = operation.id - 1; i >= 0; i--)
                {
                    if (!elements[i].turnedOff)
                    {
                        operation.left = i;
                        break;
                    }
                }
                if (operation.left == -1)
                {
                    _errorMessage = SymbologyMessageStrings.Expression_LeftOperandMissing;
                    return false;
                }
                operation.binaryOperation = true;
            }
            else
            {
                operation.binaryOperation = false;
            }

            // caching operations
            if (_saveOperations)
            {
                Operation op = new Operation();
                op.left = operation.left;
                op.right = operation.right;
                op.id = operation.id;
                op.binaryOperation = operation.binaryOperation;
                _operations.Add(op);
            }
            return true;
        }
示例#7
0
        /// <summary>
        /// Calculates the given operation for the values of the given part.
        /// </summary>
        /// <param name="part"></param>
        /// <param name="operation"></param>
        /// <returns></returns>
        private bool CalculateOperation(ExpressionPart part, Operation operation)
        {
            ExpressionValue valLeft = null;
            ExpressionValue valRight = null;
            Element elLeft = null;
            Element elRight = null;

            tkOperation oper = part.elements[operation.id].operation;

            valRight = GetValue(part, operation.right);
            elRight = part.elements[operation.right];

            if (oper == tkOperation.operNOT)   //  tis is an unary operator and we read only right operand
            {
                if (valRight.type != tkValueType.vtBoolean)
                {
                    _errorMessage = SymbologyMessageStrings.Expression_OperationNotSupported;
                    return false;
                }
                elRight.calcVal.bln = !(valRight.bln);
                elRight.calcVal.type = tkValueType.vtBoolean;
                elRight.wasCalculated = true;
                part.elements[operation.id].turnedOff = true;
            }
            else if (oper == tkOperation.operChangeSign)  // tis is an unary operator and we read only right operand
            {
                if (valRight.type != tkValueType.vtDouble)
                {
                    _errorMessage = SymbologyMessageStrings.Expression_OperationNotSupported;
                    return false;
                }
                elRight.calcVal.dbl = -valRight.dbl;
                elRight.calcVal.type = tkValueType.vtDouble;
                elRight.wasCalculated = true;
                part.elements[operation.id].turnedOff = true;
            }
            else // these are binary operators as we read left and right operands
            {
                valLeft = GetValue(part, operation.left);
                elLeft = part.elements[operation.left];

                if (oper == tkOperation.operLineBreak)
                {
                    elLeft.calcVal.str = valLeft.ToString() + Environment.NewLine + valRight.ToString();
                    elLeft.calcVal.type = tkValueType.vtString;
                }
                else if (valLeft.type == valRight.type)
                {
                    if (valLeft.type == tkValueType.vtDouble)
                    {
                        CalculateDoubleOperation(oper, elLeft, elRight, valLeft, valRight);
                    }
                    else if (valLeft.type == tkValueType.vtString)
                    {
                        CalculateStringOperation(oper, elLeft, elRight, valLeft, valRight);
                    }
                    else if (valLeft.type == tkValueType.vtBoolean)
                    {
                        CalculateBoolOperation(oper, elLeft, elRight, valLeft, valRight);
                    }
                }
                else if (oper != tkOperation.operPlus) // plus is the only operation that can have different valuetypes
                {
                    _errorMessage = SymbologyMessageStrings.Expression_OperationNotSupported;
                    return false;
                }
                else if (valLeft.type == tkValueType.vtBoolean || valRight.type == tkValueType.vtBoolean) // boolean can't be added
                {
                    _errorMessage = SymbologyMessageStrings.Expression_PlusNotAllowed;
                    return false;
                }
                else //concat strings and doubles
                {
                    elLeft.calcVal.str = valLeft.ToString() + valRight.ToString();
                    elLeft.calcVal.type = tkValueType.vtString;
                }
                elLeft.wasCalculated = true;
                part.elements[operation.id].turnedOff = true;
                part.elements[operation.right].turnedOff = true;
            }
            return true;
        }
示例#8
0
        /// <summary>
        /// Parses the given string to Expression.
        /// </summary>
        /// <param name="s"></param>
        /// <returns>True if string can be parsed to expression.</returns>
        public bool ParseExpression(string s)
        {
            _errorMessage = "";
            if (_expressionString != s)
            {
                _expressionString = s;
                _expChanged = true;
                _valid = false;
            }
            else
            {
                _expChanged = false;
                if (_valid) return true;
            }

            if (s.Length == 0) return false;

            ExpressionPart bracket = new ExpressionPart();

            _saveOperations = true;
            _variables.Clear();
            _parts.Clear();
            _operations.Clear();
            _strings.Clear();


            foreach (string c in new string[] { "{", "}" })
            {
                int pos = s.IndexOf(c);
                if (pos > -1)
                {
                    _errorMessage = "Unallowed character " + c + " at " + pos;
                    return false;
                }
            }

            Regex r = new Regex(@"\[(\d+|\w+)\]"); //all fields in [] that contain only word characters and numbers
            var matches = r.Matches(s);
            for (int i = matches.Count - 1; i >= 0; i--)
            {
                _strings.Add(matches[i].Value.Substring(1, matches[i].Length - 2));
                ReplaceSubString(ref s, matches[i].Index, matches[i].Length, "{f" + (_strings.Count - 1) + "}");
            }

            r = new Regex("(\"([^\"\n]*(\"\")*[^\"\n]*)*\")"); //everything inside "" all the same wether it contains no " or paired "
            matches = r.Matches(s);
            for (int i = matches.Count - 1; i >= 0; i--)
            {
                _strings.Add(matches[i].Value.Substring(1, matches[i].Length - 2));
                ReplaceSubString(ref s, matches[i].Index, matches[i].Length, "{s" + (_strings.Count - 1) + "}");
            }

            if (s.Contains("\""))
            {
                _errorMessage = SymbologyMessageStrings.Expression_UnpairedTextquotes;
                return false;
            }
            if (s.Contains("[]"))
            {
                _errorMessage = SymbologyMessageStrings.Expression_EmptyField;
                return false;
            }
            if (s.Contains("[") || s.Contains("]"))
            {
                _errorMessage = SymbologyMessageStrings.Expression_UnpairedBracket;
                return false;
            }

            bool found = true;
            while (found)
            {
                // seeking brackets
                int begin = 0;
                int end = 0;
                found = GetBrackets(s, ref begin, ref end);

                string expression = found ? s.Substring(begin + 1, end - begin - 1) : s;
                if (!ParseExpressionPart(expression))
                    return false;

                if (found)
                    ReplaceSubString(ref s, begin, end - begin + 1, "{p" + (_parts.Count - 1) + "}");
            }

            _strings.Clear();

            // building field list for faster access
            for (int i = 0; i < _parts.Count; i++)
            {
                ExpressionPart part = _parts[i];
                for (int j = 0; j < part.elements.Count; j++)
                {
                    if (part.elements[j].isField)
                    {
                        _variables.Add(part.elements[j]);
                    }
                }
            }

            return true;
        }