Exemplo n.º 1
0
        public void Visit(WildcardToken token)
        {
            // When * encountered,
            // Dequees all remaining tokens and passes them to a nested Evaluator.
            // Keeps seing if the nested evaluator will match, and if it doesn't then
            // will consume / match against one character, and retry.
            // Exits when match successful, or when the end of the current path segment is reached.
            GlobTokenMatch match = null;

            match = new GlobTokenMatch()
            {
                Token = token
            };
            AddMatch(match);


            var remainingText = _Reader.ReadToEnd();
            int endOfSegmentPos;

            using (var pathReader = new GlobStringReader(remainingText))
            {
                var thisPath = pathReader.ReadPathSegment();
                endOfSegmentPos = pathReader.CurrentIndex;
            }

            var remaining = _TokenQueue.ToArray();

            // if no more tokens remaining then just return as * matches the rest of the segment.
            if (remaining.Length == 0)
            {
                this.Success = true;

                match.Value = remainingText;


                return;
            }

            // we have to attempt to match the remaining tokens, and if they dont all match,
            // then consume a character, until we have matched the entirity of this segment.
            var matchedText  = new StringBuilder(endOfSegmentPos);
            var nestedEval   = new GlobTokenMatchAnalysisEvaluator(remaining);
            var pathSegments = new List <string>();

            // we keep a record of text that this wildcard matched in order to satisfy the
            // greatest number of child token matches.
            var bestMatchText = new StringBuilder(endOfSegmentPos);
            IList <GlobTokenMatch> bestMatches = null; // the most tokens that were matched.

            for (int i = 0; i < endOfSegmentPos; i++)
            {
                var matchInfo = nestedEval.Evaluate(remainingText);
                if (matchInfo.Success)
                {
                    break;
                }

                // match a single character
                matchedText.Append(remainingText[0]);
                // re-attempt matching of child tokens against this remaining string.
                remainingText = remainingText.Substring(1);
                // If we have come closer to matching, record our best results.
                if ((bestMatches == null && matchInfo.Matches.Any()) || (bestMatches != null && bestMatches.Count < matchInfo.Matches.Length))
                {
                    bestMatches = matchInfo.Matches.ToArray();
                    bestMatchText.Clear();
                    bestMatchText.Append(matchedText.ToString());
                }
            }

            this.Success = nestedEval.Success;
            if (nestedEval.Success)
            {
                // add all child matches.
                this.MatchedTokens.AddRange(nestedEval.MatchedTokens);
            }
            else
            {
                // add the most tokens we managed to match.
                if (bestMatches != null && bestMatches.Any())
                {
                    this.MatchedTokens.AddRange(bestMatches);
                }
            }

            match.Value = matchedText.ToString();
            _TokenQueue.Clear();
        }
Exemplo n.º 2
0
 private void AddMatch(GlobTokenMatch match)
 {
     this.MatchedTokens.Add(match);
     this.Success = true;
 }