[Python-bugs-list] float("1.0e-309") inconsistency on win32 (PR#245)

guido@python.org guido@python.org
Fri, 24 Mar 2000 23:12:27 -0500 (EST)


> [atof and strtod act differently given denormals on both Windows &
>  Solaris]
> 
> [Guido]
> > ...
> > Apparently strtod() and atof() differ in implementation, even though
> > the Solaris man page says "The atof(str) function call is equivalent
> > to strtod(str, (char **)NULL)."

[Tim]
> Ya, their man page is lying.  atof() existed in the mists of prehistory and
> typically did no error checking at all.  IIRC, ANSI C introduced strtod(),
> which generally got implemented as a layer of error-checking around atof.
> 
> I have to take it back that this is a bug in MS's strtod:  DBL_MIN is MS's
> limits.h is 2.2250738585072014e-308, so strtod() *should* gripe on non-zero
> inputs with absolute value smaller than that.
> 
> > We could fix this by changing float() to do its own syntax checking
> > and then use atof()...  Is it worth it?
> 
> Depends on your goal <wink>:  do you want more extreme cases, like 1e-500,
> to blow up (strtod) or underflow to 0 (atof)?  The example in the original
> test case is subtler because atof made it *appear* to be "a regular old
> number"; in fact, it's not, it's small enough that it falls into 754's
> "denormalized" range.  This means the conversion loses some extraordinary
> amount of-- but not all --information (whereas 1e-500 is below even the
> denorm range:  conversion loses all information).
> 
> Without a coherent strategy for dealing with 754 issues, it's hard to decide
> which is better.  Since strtod() is more restrictive, if this is worth
> bothering about at all now (for P3K I think 754 needs to be taken
> seriously), I actually recommend changing  current atof() calls to use
> native strtod() instead.

Hm, I'm not so sure.  Suppose I'm writing a program that reads a data
files generated by some Fortran program.  The Fortran program is
giving me points to plot for example.  If Fortran manages to output
1e-500, wouldn't it make more sense if I rounded that to zero instead
of rejecting it?  After all, after converting to plot precision it's
going to be zero anyway.

This way I could almost defend using strtod() for literals in
Python source code (where it makes more sense to warn about underflow)
but atof() for input.  Except that of course input could conceivably
be using eval()...

Another argument for turning underflow into zero is that that also
happens in regular arithmetic:

>>> 0.1**2**8
1.0000000000000275e-256
>>> 0.1**2**9
0.0

I like this uniform behavior: overflow -> exception, underflow ->
zero.  My calculator does this too.

Am I hopelessly naive about this?  What else can we do?  What control
does C give?  What does sscanf() do?

--Guido van Rossum (home page: http://www.python.org/~guido/)