System.Xml.Xsl.Xslt.QilGenerator.PlaceMarkerAny C# (CSharp) Méthode

PlaceMarkerAny() private méthode

private PlaceMarkerAny ( QilNode countPattern, QilNode fromPattern ) : QilNode
countPattern QilNode
fromPattern QilNode
Résultat QilNode
        private QilNode PlaceMarkerAny(QilNode countPattern, QilNode fromPattern)
        {
            /*
                Quotation from XSLT 2.0 spec:
                * If the context node is a document node, return the empty sequence, ()
                * Let $A be the node sequence selected by the expression
                    (preceding::node()|ancestor-or-self::node())[matches-count(.)]
                * Let $F be the node sequence selected by the expression
                    (preceding::node()|ancestor::node())[matches-from(.)][last()]
                * Let $AF be the node sequence $A[. is $F or . >> $F].
                * If $AF is empty, return the empty sequence, ()
                * Otherwise return the value of the expression count($AF)

                NOTE: There are some distinctions between XSLT 1.0 and XSLT 2.0 specs. In our 1.0 implementation we:
                1) Assume that the 'matches-from()' function does not match root nodes by default.
                2) Instead of '$A[. is $F or . >> $F]' we calculate
                     '$A'           if the 'from' attribute is omitted,
                     '$A[. >> $F]'  if the 'from' attribute is present.
            */

            QilNode range, fromMatches, F, AF;
            QilIterator i, j, k;

            if (fromPattern == null)
            {
                // According to XSLT 2.0 spec, if the 'from' attribute is omitted, matches-from() returns true
                // only for the root node. It means $F is a sequence of length one containing the root node,
                // and $AF = $A. XSLT 1.0 spec rules lead to the same result $AF = $A, so two specs are compliant here.
                range = _f.NodeRange(_f.Root(GetCurrentNode()), GetCurrentNode());
                AF = _f.Filter(i = _f.For(range), MatchCountPattern(countPattern, i));
            }
            else
            {
                fromMatches = _f.Filter(i = _f.For(_f.Preceding(GetCurrentNode())), MatchPattern(fromPattern, i));
                F = _f.Filter(i = _f.For(fromMatches), _f.Eq(_f.PositionOf(i), _f.Int32(1)));
                AF = _f.Loop(i = _f.For(F),
                    _f.Filter(j = _f.For(_f.Filter(k = _f.For(_f.NodeRange(i, GetCurrentNode())), MatchCountPattern(countPattern, k))),
                        _f.Not(_f.Is(i, j))
                    )
                );
            }

            return _f.Loop(k = _f.Let(_f.Length(AF)),
                _f.Conditional(_f.Eq(k, _f.Int32(0)), _f.Sequence(),
                k
            ));
        }
QilGenerator