Exemplo n.º 1
0
 XmlGraphNode IExprVisitor <XmlGraphNode> .VisitChars(CharsExpr charsExpr)
 {
     return(this.Graph.CreateNode());
 }
Exemplo n.º 2
0
        Expr ParseImpl(Token[] tokens, int from, int to)
        {
            var items        = new LinkedList <Expr>();
            var makeOr       = false;
            var makeCheck    = false;
            var makeCheckNot = false;

            for (int i = from; i <= to; i++)
            {
                var t = tokens[i];

                switch (t.kind)
                {
                case TokenKind.openGroup:
                    var nextPos   = this.SkipBraces(tokens, i + 1, to);
                    var groupNode = this.ParseImpl(tokens, i + 1, nextPos - 1);
                    if (groupNode == null)
                    {
                        return(null);
                    }
                    i = nextPos;
                    items.AddLast(groupNode);
                    break;

                case TokenKind.closeGroup:
                    return(null);

                case TokenKind.checkOp:
                    makeCheck = true;
                    continue;

                case TokenKind.checkNotOp:
                    makeCheckNot = true;
                    continue;

                case TokenKind.orOp:
                    makeOr = true;
                    continue;

                case TokenKind.quantor:
                    int minNum = -1, maxNum = -1;
                    this.ParseQuantifier(t.str, ref minNum, ref maxNum);

                    Expr lastExprPart;
                    if (items.Last.Value is CharsExpr chars)
                    {
                        lastExprPart = new CharsExpr(chars.Chars.Last().ToString());
                        items.RemoveLast();
                        items.AddLast(new CharsExpr(chars.Chars.Substring(0, chars.Chars.Length - 1)));
                    }
                    else
                    {
                        lastExprPart = items.Last.Value;
                        items.RemoveLast();
                    }

                    items.AddLast(Expr.Number(lastExprPart, minNum, maxNum));
                    break;

                case TokenKind.charClass:
                    var classAlts = this.ParseCharClass(tokens, ref i);
                    items.AddLast(classAlts);
                    break;

                case TokenKind.anyChar:
                    items.AddLast(Expr.AnyChar());
                    break;

                case TokenKind.ch:
                    items.AddLast(Expr.Characters(t.str));
                    break;

                case TokenKind.escapedChar:
                    items.AddLast(GiveEscape(t));
                    break;

                case TokenKind.rangeOp:
                    return(null);

                default:
                    throw new NotImplementedException("");
                }

                if (makeOr)
                {
                    if (makeCheck || makeCheckNot)
                    {
                        return(null);
                    }

                    if (items.Count < 2)
                    {
                        return(null);
                    }

                    var nextPos = i + 1;
                    if (nextPos <= to)
                    {
                        if (tokens[nextPos].Check(TokenKind.quantor))
                        {
                            continue;
                        }
                    }

                    var lastItemIfAlts   = items.Last.Previous.Value as AlternativesExpr;
                    var newAltesChildren = lastItemIfAlts == null ? new[] { items.Last.Previous.Value, items.Last.Value }
                                            : lastItemIfAlts.Items.Concat(new[] { items.Last.Value }).ToArray();

                    var newAltsNode = Expr.Alternatives(newAltesChildren);
                    items.RemoveLast();
                    items.RemoveLast();
                    items.AddLast(newAltsNode);
                    makeOr = false;
                }
                else if (makeCheck)
                {
                    if (makeOr || makeCheckNot)
                    {
                        return(null);
                    }

                    var lastExprPart = items.Last.Value;
                    items.RemoveLast();
                    items.AddLast(Expr.Check(lastExprPart));
                    makeCheck = false;
                }
                else if (makeCheckNot)
                {
                    if (makeCheck || makeOr)
                    {
                        return(null);
                    }

                    var lastExprPart = items.Last.Value;
                    items.RemoveLast();
                    items.AddLast(Expr.CheckNot(lastExprPart));
                    makeCheckNot = false;
                }
            }

            return(Expr.Sequence(items.ToArray()));
        }