Tk Library Source Code

View Ticket
Login
Ticket UUID: 2691870
Title: determineScale with close numbers
Type: Bug Version: None
Submitter: relaxmike Created on: 2009-03-18 14:15:00
Subsystem: tklib :: plotchart Assigned To: arjenmarkus
Priority: 5 Medium Severity:
Status: Closed Last Modified: 2009-03-21 01:25:27
Resolution: Fixed Closed By: arjenmarkus
    Closed on: 2009-03-20 18:19:51
Description:
Hi,
With Plotchart 1.6.1, used in Tcl 8.4.

% package require Plotchart
1.6.1
% Plotchart::determineScale 0.99999999999999911  1.0000000000000007
integer value too large to represent

The cause is in the computation of nicemin :

set nicemin [expr {$step*$factor*int($xmin/$factor/$step)}]

Here the value of the factor is very low :

dx = 1.55431223448e-015
expon = -14
factor = 1e-014
step = 0.2
xmin = 0.99999999999999911

so that the value $xmin/$factor/$step is not representable as a 32 bit integer, used in Tcl 8.4.
In fact, the relative shift between the 
two numbers is 1.e-15, very close to the 
precision of double precision floating 
point numbers.

A possible fix is to compute the relative shift,
and to modify the inputs so that at least 8 significant digits are different.
The modified version gives the result :

% catch {Plotchart::determineScale 0.99999999999999911  1.0000000000000007 0 8} errmsg ; set errmsg
expon = -8
factor = 1e-008
step = 0.2
xmin = 0.999999995
0.999999994 1.000000006 2e-009

The patched version is in attachment of the bug report.

Best regards,

Michael
User Comments: arjenmarkus added on 2009-03-21 01:19:51:

allow_comments - 1

Done - it now works fine

arjenmarkus added on 2009-03-20 14:53:28:
I thought I could fix this easily with the wide() function and restricting the
range. That was not as easy as it looks. But I think I have a solution: make
sure that there is a reasonable range - that is: abs(xmax-xmin) should not 
be smaller than 1.0e-10*abs(xmax+xmin), say. So: first check that. If it 
fails, recompute xmin and xmax (you forgot the patch for scaling.tcl, but 
that does not matter).

Allowing even smaller ranges is not wise: the precision of the numbers will
come into play!

andreas_kupries added on 2009-03-20 00:19:03:
Maybe talk to Kevin Kenny as well, IIRC he knows quite a bit about (floating) math.

arjenmarkus added on 2009-03-19 14:45:39:
I have seen a related behaviour (Tcl 8.5) with the labels on the axis:
An axis with the labels 0.0 0.2 ... 1.0 also gives a label like 0.6000000001.

We will have to investigate this - certainly a runtime error is unacceptable.

relaxmike added on 2009-03-18 21:31:38:
I'am not sure that the result is improved.
Suppose that the tcl precision is set to the max and 
you still get "not so nice" numbers :

set ::tcl_precision 17
catch {Plotchart::determineScale 0.99999999999999711  1.0000000000000007} errmsg ; set errmsg
determineScale : xmin = 0.99999999999999711 xmax = 1.0000000000000007
shift = 3.5527136788004986e-015
re = 1e-008
expon = -8
factor = 1e-008
step = 0.2
xmin = 0.99999999499999714
0.99999999400000006 1.0000000060000001 2.0000000000000001e-009

So my fix seems to be unefficient here and I don't exactly 
what to do...

relaxmike added on 2009-03-18 21:16:23:

File Added - 318371: plotchart.test

File Added: plotchart.test

relaxmike added on 2009-03-18 21:16:05:

File Added - 318370: plotchart.test

File Added: plotchart.test

relaxmike added on 2009-03-18 21:15:00:

File Added - 318369: plotchart.tcl

Attachments: