Пример #1
0
        /*
         *   LocationPathPattern ::= '/' RelativePathPattern? | '//'? RelativePathPattern | IdKeyPattern (('/' | '//') RelativePathPattern)?
         */
        private QilNode ParseLocationPathPattern()
        {
            QilNode opnd;

            switch (_scanner.Kind)
            {
            case LexKind.Slash:
                _scanner.NextLex();
                opnd = _ptrnBuilder.Axis(XPathAxis.Root, XPathNodeType.All, null, null);

                if (XPathParser.IsStep(_scanner.Kind))
                {
                    opnd = _ptrnBuilder.JoinStep(opnd, ParseRelativePathPattern());
                }
                return(opnd);

            case LexKind.SlashSlash:
                _scanner.NextLex();
                return(_ptrnBuilder.JoinStep(
                           _ptrnBuilder.Axis(XPathAxis.Root, XPathNodeType.All, null, null),
                           _ptrnBuilder.JoinStep(
                               _ptrnBuilder.Axis(XPathAxis.DescendantOrSelf, XPathNodeType.All, null, null),
                               ParseRelativePathPattern()
                               )
                           ));

            case LexKind.Name:
                if (_scanner.CanBeFunction && _scanner.Prefix.Length == 0 && (_scanner.Name == "id" || _scanner.Name == "key"))
                {
                    opnd = ParseIdKeyPattern();
                    switch (_scanner.Kind)
                    {
                    case LexKind.Slash:
                        _scanner.NextLex();
                        opnd = _ptrnBuilder.JoinStep(opnd, ParseRelativePathPattern());
                        break;

                    case LexKind.SlashSlash:
                        _scanner.NextLex();
                        opnd = _ptrnBuilder.JoinStep(opnd,
                                                     _ptrnBuilder.JoinStep(
                                                         _ptrnBuilder.Axis(XPathAxis.DescendantOrSelf, XPathNodeType.All, null, null),
                                                         ParseRelativePathPattern()
                                                         )
                                                     );
                        break;
                    }
                    return(opnd);
                }
                break;
            }
            opnd = ParseRelativePathPattern();
            return(opnd);
        }