predicates in xslt

Predicates

1. when do we use the [ ] and when do we use ( )?
2. Not equals

1.

when do we use the [ ] and when do we use ( )?

Jeni Tennison



> i have a basic doubt regarding conditions..
> what is the difference between saying
> <xsl:if test = "not[. = mytag/mytext]">
> and the same using ()

This is testing whether the 'not' child element of the current node has a value that is equal to the value of (one of) its child 'mytag' elements's child 'mytext' elements.

> and saying
>
> <xsl:if test = "not(. = mytag/mytext)">

This is testing whether it's not the case that the value of the current node is equal to the value of (one of) its child 'mytag' elements's child 'mytext' elements.

> when do we use the [ ] and when do we use ( )??

[]s are predicates -- they are used to filter node sets according to some condition. So for example:

  book[title = 'Genesis']

locates the book element child of the current node whose title element child has the value 'Genesis'.

()s are used to wrap around expressions to indicate priority. So for example:

  (a and b) or c

is different from:

  a and (b or c)

Or, in the case that you've shown above, they're used after the name of a function to hold the arguments for that function. not(), for example, is a function that negates the boolean value of whatever's passed as its argument.

()s are also used as part of node tests, so for example the expression:

  text()

is a shorthand for:

  child::text()

and collects all the text nodes that are children of the current node.

2.

Not equals

Jeni Tennison



> I've got a stylesheet that produces different results depending on
> whether I use "A != B" or "not(A = B)"? Is this supposed to happen?
> Can someone explain why? It's not very intuitive.

The reason for the difference lies in how comparisons between node sets work in XSLT. Whenever you compare two node sets, the comparison returns true if the comparison would be true for any similar comparisons on the individual nodes in that node set.

Expanding the comparison (using a slightly adapted form of XPath 2.0 syntax) makes this easier to understand: A != B is equivalent to:

  some $a in A, $b in B satisfies $a != $b

This returns true when there is any combination of $a and $b that aren't equal; the only time this isn't the case is if all the $as in A are equal and all the $bs in B are equal, and they're all equal to each other.

On the other hand not(A = B) is equivalent to:

  not(some $a in A, $b in B satisfies $a = $b)

This returns true when there isn't any combination of $a and $b that are equal. This is generally what you want.