Project

Profile

Help

Bug #3457

closed

switch, xs:QName

Added by Christian Grün about 7 years ago. Updated about 7 years ago.

Status:
Closed
Priority:
Low
Assignee:
Category:
XQuery conformance
Sprint/Milestone:
-
Start date:
2017-09-22
Due date:
% Done:

100%

Estimated time:
Legacy ID:
Applies to branch:
9.8
Fix Committed on Branch:
9.8
Fixed in Maintenance Release:
Platforms:

Description

With Saxon-EE 9.7.0.8J, the following query returns 2 instead of 1:

let $v := xs:QName('a')
return switch($v)
  case $v return 1
  default return 2
Actions #1

Updated by Christian Grün about 7 years ago

Possibly related:

let $v := xs:date('2001-01-01')
return switch($v)
  case $v return 1
  default return 2

This query raises the error »Dynamic context missing: Unknown implicit timezone«.

Actions #2

Updated by Michael Kay about 7 years ago

Thanks for reporting it. Looking first at the QName case:

I have made this into QT3 test case switch-014 (yes, the test number gives a clue that the test coverage for this new feature is somewhat minimal...)

The switch expression compiles internally into a construct that uses an EquivalenceExpression, presumably on the basis that the comparison semantics for switch are sufficiently different from other comparison expressions. The EquivalenceExpression in turn is making use of an AtomicSortComparer, but this is designed primarily to do ordering comparisons and it is failing on values that do not support ordered comparison. Specifically, it fails because it calls getXPathComparable() on each of the operands, and getXPathComparable() on an xs:QName returns null, and if either comparison key is null the comparison is deemed to return false.

It seems the EquivalenceExpression is used only for this purpose. It's not immediately clear why we need it. The semantics of the switch expression are described in terms of a call on deep-equal(). I tried generating a deep-equal() call in place of the EquivalenceExpression, with appropriate addition of Atomizers and CardinalityCheckers, and I get one test failure: switch-902. This appears to be because deep-equal is returning a false() result before the cardinality check activates. However, closer examination reveals why it wasn't implemented this way: an EquivalenceExpression makes the code eligible for optimization to use a hash lookup when the keys are constants.

It seems incorrect that the EquivalenceComparer should inherit from AtomicSortComparer. What deep-equal() does is to use a GenericAtomicComparer, but customised with NaN=NaN semantics. It would be good to allocate a more specific comparer if the types are known statically.

Actions #3

Updated by Michael Kay about 7 years ago

  • Category set to XQuery conformance
  • Status changed from New to Resolved
  • Assignee set to Michael Kay
  • Applies to branch 9.8 added
  • Fix Committed on Branch 9.8 added

Rewrote the EquivalenceComparer used for the XQuery switch expression. It now inherits from GenericAtomicComparer rather than AtomicSortComparer. It includes the logic to accept a run-time dynamic context for use when the comparison depends on the implicit timezone.

Various additional tests added to prod-SwitchExpr test set in QT3.

Actions #4

Updated by O'Neil Delpratt about 7 years ago

  • Status changed from Resolved to Closed
  • % Done changed from 0 to 100
  • Fixed in Maintenance Release 9.8.0.5 added

Bug fix applied in the Saxon 9.8.0.5 maintenance release.

Please register to edit this issue

Also available in: Atom PDF