示例#1
0
        private void Combinator(char combinator)
        {
            tq.ConsumeWhitespace();
            string subQuery = ConsumeSubQuery();                    // support multi > childs

            Evaluator rootEval;                                     // the new topmost evaluator
            Evaluator currentEval;                                  // the evaluator the new eval will be combined to. could be root, or rightmost or.
            Evaluator newEval          = Parse(subQuery, _options); // the evaluator to add into target evaluator
            bool      replaceRightMost = false;

            if (evals.Count == 1)
            {
                rootEval = currentEval = evals[0];
                // make sure OR (,) has precedence:
                if (rootEval is CombiningEvaluator.Or && combinator != ',')
                {
                    currentEval      = ((CombiningEvaluator.Or)currentEval).RightMostEvaluator();
                    replaceRightMost = true;
                }
            }

            else
            {
                rootEval = currentEval = new CombiningEvaluator.And(evals);
            }
            evals.Clear();

            // for most combinators: change the current eval into an AND of the current eval and the new eval
            switch (combinator)
            {
            case '>':
                currentEval = new CombiningEvaluator.And(newEval, new StructuralEvaluator.ImmediateParent(currentEval));
                break;

            case ' ':
                currentEval = new CombiningEvaluator.And(newEval, new StructuralEvaluator.Parent(currentEval));
                break;

            case '+':
                currentEval = new CombiningEvaluator.And(newEval, new StructuralEvaluator.ImmediatePreviousSibling(currentEval));
                break;

            case '~':
                currentEval = new CombiningEvaluator.And(newEval, new StructuralEvaluator.PreviousSibling(currentEval));
                break;

            case ',':     // group or.
                CombiningEvaluator.Or or = currentEval as CombiningEvaluator.Or;
                if (or != null)
                {
                    or.Add(newEval);
                }
                else
                {
                    or = new CombiningEvaluator.Or();
                    or.Add(currentEval);
                    or.Add(newEval);
                }
                currentEval = or;
                break;

            default:
                throw DomFailure.UnknownCombinator(combinator);
            }

            if (replaceRightMost)
            {
                ((CombiningEvaluator.Or)rootEval).ReplaceRightMostEvaluator(currentEval);
            }
            else
            {
                rootEval = currentEval;
            }
            evals.Add(rootEval);
        }
示例#2
0
        private void Combinator(char combinator)
        {
            tq.ConsumeWhitespace();
            string subQuery = ConsumeSubQuery(); // support multi > childs

            Evaluator rootEval; // the new topmost evaluator
            Evaluator currentEval; // the evaluator the new eval will be combined to. could be root, or rightmost or.
            Evaluator newEval = Parse(subQuery); // the evaluator to add into target evaluator
            bool replaceRightMost = false;

            if (evals.Count == 1) {
                rootEval = currentEval = evals[0];
                // make sure OR (,) has precedence:
                if (rootEval is CombiningEvaluator.Or && combinator != ',') {
                    currentEval = ((CombiningEvaluator.Or) currentEval).RightMostEvaluator();
                    replaceRightMost = true;
                }
            }

            else {
                rootEval = currentEval = new CombiningEvaluator.And(evals);
            }
            evals.Clear();

            // for most combinators: change the current eval into an AND of the current eval and the new eval
            switch (combinator) {

                case '>':
                    currentEval = new CombiningEvaluator.And(newEval, new StructuralEvaluator.ImmediateParent(currentEval));
                    break;

                case ' ':
                    currentEval = new CombiningEvaluator.And(newEval, new StructuralEvaluator.Parent(currentEval));
                    break;

                case '+':
                    currentEval = new CombiningEvaluator.And(newEval, new StructuralEvaluator.ImmediatePreviousSibling(currentEval));
                    break;

                case '~':
                    currentEval = new CombiningEvaluator.And(newEval, new StructuralEvaluator.PreviousSibling(currentEval));
                    break;

                case ',': // group or.
                    CombiningEvaluator.Or or = currentEval as CombiningEvaluator.Or;
                    if (or != null) {
                        or.Add(newEval);

                    } else {
                        or = new CombiningEvaluator.Or();
                        or.Add(currentEval);
                        or.Add(newEval);
                    }
                    currentEval = or;
                    break;

                default:
                    throw DomFailure.UnknownCombinator(combinator);
            }

            if (replaceRightMost)
                ((CombiningEvaluator.Or) rootEval).ReplaceRightMostEvaluator(currentEval);
            else rootEval = currentEval;
            evals.Add(rootEval);
        }