[Bug 2644] [F+O] Conversion from float/double to string

http://www.w3.org/Bugs/Public/show_bug.cgi?id=2644

           Summary: [F+O] Conversion from float/double to string
           Product: XPath / XQuery / XSLT
           Version: Candidate Recommendation
          Platform: PC
        OS/Version: Windows XP
            Status: NEW
          Severity: normal
          Priority: P2
         Component: Functions and Operators
        AssignedTo: ashok.malhotra@oracle.com
        ReportedBy: mike@saxonica.com
         QAContact: public-qt-comments@w3.org


The rules for conversion of a float or double to a string do not give an
unambiguous answer. The rule as stated in 17.1.2 is:

Beyond the one required digit after the decimal point in the mantissa, there
must be as many, but only as many, additional digits as are needed to uniquely
distinguish the value from all other values for the datatype after rounding the
final digit.

Most of this comes straight from XPath 1.0, except for the phrase "after
rounding the final digit". I've no idea what that phrase is supposed to mean.
Final digit of what, pray?

Having dealt with that, what does the rest mean?

The particular test case that gave rise to this bug report is casthcds14. This
generates a float value whose internal IEEE representation is x

Consider, for example, the float whose internal IEEE representation is
x58901723. The table below shows that this can be produced by parsing any string
in the range 1.26743230E15 to 1.26743243E15. What is the correct string
representation of this float value? The expected test results are stated as
1.26743233E15. Saxon (and Java) produce 1.26743237E15. The only way I can read
the spec, however, suggests that the result should be 1.2674323E15.

And even if we can decide what the rules really mean, is there a known efficient
algorithm for implementing them?

The Java rule is clear and unambiguous:

[Where m is the mantissa] Let n  be the unique integer such that 10^n <= m <
10^n+1; then let a be the mathematically exact quotient of m and 10^n so that 1
<= a < 10. The magnitude is then represented as the integer part of a, as a
single decimal digit, followed by '.' ('\u002E'), followed by decimal digits
representing the fractional part of a.

I would propose that we adopt the Java rules.


Table: 
Column 1: a string
Column 2: the internal (hexadecimal) representation of the IEEE float produced
by parsing this string as a float 
Column 3: the Java string representation of the float in column 2. As it
happens, in this sequence 7 digits after the decimal point are always enough to
distinguish the value. But will this always be the case, and how does one know?

1.26743200E15 = 58901720 = 1.26743196E15
1.26743201E15 = 58901720 = 1.26743196E15
1.26743202E15 = 58901720 = 1.26743196E15
1.26743203E15 = 58901720 = 1.26743196E15
1.26743204E15 = 58901721 = 1.2674321E15
1.26743205E15 = 58901721 = 1.2674321E15
1.26743206E15 = 58901721 = 1.2674321E15
1.26743207E15 = 58901721 = 1.2674321E15
1.26743208E15 = 58901721 = 1.2674321E15
1.26743209E15 = 58901721 = 1.2674321E15
1.26743210E15 = 58901721 = 1.2674321E15
1.26743211E15 = 58901721 = 1.2674321E15
1.26743212E15 = 58901721 = 1.2674321E15
1.26743213E15 = 58901721 = 1.2674321E15
1.26743214E15 = 58901721 = 1.2674321E15
1.26743215E15 = 58901721 = 1.2674321E15
1.26743216E15 = 58901721 = 1.2674321E15
1.26743217E15 = 58901722 = 1.26743223E15
1.26743218E15 = 58901722 = 1.26743223E15
1.26743219E15 = 58901722 = 1.26743223E15
1.26743220E15 = 58901722 = 1.26743223E15
1.26743221E15 = 58901722 = 1.26743223E15
1.26743222E15 = 58901722 = 1.26743223E15
1.26743223E15 = 58901722 = 1.26743223E15
1.26743224E15 = 58901722 = 1.26743223E15
1.26743225E15 = 58901722 = 1.26743223E15
1.26743226E15 = 58901722 = 1.26743223E15
1.26743227E15 = 58901722 = 1.26743223E15
1.26743228E15 = 58901722 = 1.26743223E15
1.26743229E15 = 58901722 = 1.26743223E15
1.26743230E15 = 58901723 = 1.26743237E15
1.26743231E15 = 58901723 = 1.26743237E15
1.26743232E15 = 58901723 = 1.26743237E15
1.26743233E15 = 58901723 = 1.26743237E15
1.26743234E15 = 58901723 = 1.26743237E15
1.26743235E15 = 58901723 = 1.26743237E15
1.26743236E15 = 58901723 = 1.26743237E15
1.26743237E15 = 58901723 = 1.26743237E15
1.26743238E15 = 58901723 = 1.26743237E15
1.26743239E15 = 58901723 = 1.26743237E15
1.26743240E15 = 58901723 = 1.26743237E15
1.26743241E15 = 58901723 = 1.26743237E15
1.26743242E15 = 58901723 = 1.26743237E15
1.26743243E15 = 58901723 = 1.26743237E15
1.26743244E15 = 58901724 = 1.2674325E15
1.26743245E15 = 58901724 = 1.2674325E15
1.26743246E15 = 58901724 = 1.2674325E15
1.26743247E15 = 58901724 = 1.2674325E15
1.26743248E15 = 58901724 = 1.2674325E15
1.26743249E15 = 58901724 = 1.2674325E15
1.26743250E15 = 58901724 = 1.2674325E15
1.26743251E15 = 58901724 = 1.2674325E15
1.26743252E15 = 58901724 = 1.2674325E15
1.26743253E15 = 58901724 = 1.2674325E15
1.26743254E15 = 58901724 = 1.2674325E15
1.26743255E15 = 58901724 = 1.2674325E15
1.26743256E15 = 58901724 = 1.2674325E15
1.26743257E15 = 58901725 = 1.26743264E15
1.26743258E15 = 58901725 = 1.26743264E15
1.26743259E15 = 58901725 = 1.26743264E15
1.26743260E15 = 58901725 = 1.26743264E15
1.26743261E15 = 58901725 = 1.26743264E15
1.26743262E15 = 58901725 = 1.26743264E15
1.26743263E15 = 58901725 = 1.26743264E15
1.26743264E15 = 58901725 = 1.26743264E15
1.26743265E15 = 58901725 = 1.26743264E15
1.26743266E15 = 58901725 = 1.26743264E15
1.26743267E15 = 58901725 = 1.26743264E15
1.26743268E15 = 58901725 = 1.26743264E15
1.26743269E15 = 58901725 = 1.26743264E15
1.26743270E15 = 58901725 = 1.26743264E15
1.26743271E15 = 58901726 = 1.26743277E15
1.26743272E15 = 58901726 = 1.26743277E15
1.26743273E15 = 58901726 = 1.26743277E15
1.26743274E15 = 58901726 = 1.26743277E15
1.26743275E15 = 58901726 = 1.26743277E15
1.26743276E15 = 58901726 = 1.26743277E15
1.26743277E15 = 58901726 = 1.26743277E15
1.26743278E15 = 58901726 = 1.26743277E15
1.26743279E15 = 58901726 = 1.26743277E15
1.26743280E15 = 58901726 = 1.26743277E15
1.26743281E15 = 58901726 = 1.26743277E15
1.26743282E15 = 58901726 = 1.26743277E15
1.26743283E15 = 58901726 = 1.26743277E15
1.26743284E15 = 58901727 = 1.2674329E15
1.26743285E15 = 58901727 = 1.2674329E15
1.26743286E15 = 58901727 = 1.2674329E15
1.26743287E15 = 58901727 = 1.2674329E15
1.26743288E15 = 58901727 = 1.2674329E15
1.26743289E15 = 58901727 = 1.2674329E15
1.26743290E15 = 58901727 = 1.2674329E15
1.26743291E15 = 58901727 = 1.2674329E15
1.26743292E15 = 58901727 = 1.2674329E15
1.26743293E15 = 58901727 = 1.2674329E15
1.26743294E15 = 58901727 = 1.2674329E15
1.26743295E15 = 58901727 = 1.2674329E15
1.26743296E15 = 58901727 = 1.2674329E15
1.26743297E15 = 58901727 = 1.2674329E15
1.26743298E15 = 58901728 = 1.26743304E15
1.26743299E15 = 58901728 = 1.26743304E15

Received on Thursday, 5 January 2006 15:01:00 UTC