Subject: Re: [xsl] Numeric top-level predicates in patterns|
From: "Abel Braaksma (Exselt)" <abel@xxxxxxxxxx>
Date: Wed, 02 Apr 2014 19:05:46 +0200
On 2-4-2014 17:15, Michael Kay wrote: >> The rules I am after is, in this order: >> 1) numerical predicates lower than zero never select anything > More precisely, the only numerical predicates that can select anything are positive integers. Yes, I should've said "lower than or equal to". But "positive integers" is better, because it also emphasizes that a predicate such as [3.14] will never select anything. >> 2) a sibling numerical predicate that is one is always redundant in a >> pattern > "Sibling numerical predicate" isn't one of your defined terms. I assume you mean a predicate of  preceded by another numerical predicate. I thought it would be clear from the definitions of sibling predicates and numerical predicates. But indeed, I meant a numerical predicate that is also a sibling predicate, that has the effective static numeric value of 1 (the integer, not the string), such like [xs:integer(1.2)] [number("1")]  [(1 to 20)] >> 3) a sibling predicate that is a sibling of a numeric predicate that is >> higher than one never selects anything >> >> Then, to make it tricky, what happens here, if the applied set is //foo? >> (foo) > This never selects anything, but (.//foo) does. The difference is that foo always selects 0 or 1 elements, whereas .//foo may select more than one. I should have emphasized that I meant patterns, not expressions. (.//foo) is not allowed in a pattern. In XSLT 3.0, you can do .[(.//foo)] though, which gets interesting, but is not the same. Let me try a few variants, for the excercise, and see if the same rules still apply: Selects of each second descendant element foo the second item <xsl:apply-templates select="(//foo)" /> Matches never, as foo is always ever one node <xsl:template match="(foo)" /> Matches never, because of the singleton focus on the current node <xsl:template match="(//foo)" /> XSLT 3.0 syntax, matches if current node has at least two second foo descendants (uncanningly unrelated to the select-expression (//foo)). <xsl:template match=".[(.//foo)]" /> Note that the above is not equal to this: <xsl:template match=".[(//foo)]" /> The matching pattern that selects the same node as the expression (//foo) is, I think, node()/foo, assuming the apply-templates is done on a selection that includes these foo elements. Hmm, not quite. Because the pattern does not have a relation to the context item that was used during evaluation of the expression, but it gets close. >> Bottom line is, I think, that creating multiple sibling numerical >> predicates is (usually) counter-productive and won't match anything when >> used in a pattern (unless the number is "1", in which case it is also >> redundant). >> > More generally, an expression using a numeric predicate returns a value with cardinality 0:1, and applying a numeric predicate to a value with cardinality 0:1 is pointless. Yes, that's a lot clearer and more generally applicable.