MathGroup Archive 2001

[Date Index] [Thread Index] [Author Index]

Search the Archive

RE: Zero does not equal Zero

  • To: mathgroup at
  • Subject: [mg31388] RE: [mg31360] Zero does not equal Zero
  • From: "Wolf, Hartmut" <Hartmut.Wolf at>
  • Date: Wed, 31 Oct 2001 19:59:09 -0500 (EST)
  • Sender: owner-wri-mathgroup at

> -----Original Message-----
> From: Ersek, Ted R [mailto:ErsekTR at]
To: mathgroup at
> Sent: Tuesday, October 30, 2001 10:36 AM
> To: mathgroup at
> Subject: [mg31388] [mg31360] Zero does not equal Zero
> Hello Group,
> It seems people didn't fully grasp the inconsistency that I 
> pointed to in my earlier message with the same subject.  
> I came across this problem when I tried to make my 
> RootSearch package (recent MathSource addition) capable of
> finding roots to a an arbitrary precision.  To allow that I 
> had to make a function similar to Ulp[x] in the 
> NumericalMath`Microscope` package. Among other things my 
> version of Ulp can work with arbitrary  precision numbers.
> Unfortunately I can't make RootSearch work as well as I would 
> like because of the problem I demonstrate below. 
> First consider the next line which demonstrates that a 
> StandardForm output such as (0.  x 10^-20) represents an 
> arbitrary precision number that is more or less zero.
> In[1]:=
>    x=Exp[ N[Pi/3, 20] ];
>    x-x
> Out[1]=
>    0. x 10^-20
> Now suppose we want to find the arbitrary precision number 
> that is slightly larger than x, but as close as possible 
> to x and still a different number. What do I mean when 
> I say "a different number"?  Well if x and y are
> different numbers their difference should not be zero.  In 
> the first case below I view x and y as essentially the same number.
> In[2]:=
>    y=x+SetPrecision[5.96*^-20, 30];
>    {y-x, y-x==0}
> Out[4]=
>    {0. x 10^-20, True}
> What about the next case.  Here the StandardForm of (x-y) 
> looks like zero, but (x-y==0) returns False.  
>  Are x and y "different numbers"? Why does
> (x-y) return False in the next line, but True in the slightly 
> different case above?  I think when comparing numeric values
> (x-y==0) should return True IF AND ONLY IF  the StandardForm 
> of (x-y) is zero.  When I say "is zero", that includes 
> (0. x 10^-20) and similar output.
> In[5]:=
>    y=x+SetPrecision[5.97*^-20, 30];
>    {y-x, y-x==0}
> Out[6]
>    {0. x 10^-20, False}
> --------
> Regards,
>   Ted Ersek

Hello Ted,

I would not like to say what Mathematica should do or not, rather observe
what she does. Before doing so let's have a look into The Book (§3.1.5
Arbitrary-Precision Numbers):

The fact that different ways of doing the same calculation can give you
different numerical answers means, among other things, that comparisons
between approximate real numbers must be treated with care. In testing
whether two real numbers are "equal", Mathematica effectively finds their
difference, and tests whether the result is "consistent with zero" to the
precision given.  

Ignoring that word "effectively", disliked by me, let's try to find out what
"consistent with zero, to the precision given" might mean:

As the precise behaviour might vary, my machine is

In[1]:= {$Version, $MachineType, $ProcessorType, $OperatingSystem}
{"4.0 for Microsoft Windows (April 21, 1999)", "PC", "x86", "WindowsNT"}

Instead of judging from StandartForm let's look at our results in InputForm,
and also for a certain reason let's decrease $MinPrecision below zero.

In[2]:= $MinPrecision = -1;

In[3]:= x = Exp[N[Pi/3, 20]];
        x - x // InputForm

(Plain zero of course, no precision can be given, but a certain accuracy)

Now we take three different nearby values:
y1 = x + SetPrecision[0.597*^-19, 30];
{y - x, y - x == 0} // InputForm
{5.97`-0.0007*^-20, True}
y = x + SetPrecision[0.598*^-19, 30];
{y - x, y - x == 0} // InputForm
{5.98`0*^-20, True}
y2 = x + SetPrecision[0.599*^-19, 30];
{y2 - x, y2 - x == 0} // InputForm
{5.99`0.0007*^-20, False}

y1 and y are considered to be equal to x, y2 not.
We look at the accurate Precisions:
{prec1, acc1} = Through@{Precision, Accuracy}[y1 - x, Round -> False]
Out[11]= {-0.000723805, 19.2233}
{prec, acc} = Through@{Precision, Accuracy}[y - x, Round -> False]
Out[12]= {3.048266694770595`*^-6, 19.223301864278284`}
{prec2, acc2} = Through@{Precision, Accuracy}[y2 - x, Round -> False]
{0.000728687, 19.2233}
We clearly recognize that "y-x" is a borderline case. 
For y1-x we see that the precision is smaller than zero, which means the
error (due to that precision) is greater that the value, such is "consistent
with zero", for y2-x the error is less, so the value can be decided to be
positve, what Mathematica does in both cases.

Using accuracy, subtracting from the value, we come to a similar conclusion:

(y1 - x) - 10^-SetPrecision[acc1, 40] // InputForm
Out[14]//InputForm= -9.9580271645`-2.7785*^-23
(y - x) - 10^-SetPrecision[acc, 40] // InputForm
Out[15]//InputForm= 4.19728355`-5.1537*^-25
(y2 - x) - 10^-SetPrecision[acc2, 40] // InputForm
Out[16]//InputForm= 1.00419728355`-2.7749*^-22

Again we would say that y-x is at "zero crossing". 
I would not call the case y-x==0 to be an error, rather 
it is astonishing that y1-x, and y2-x come out right, 
considering the precision given for x.

-- Hartmut Wolf

  • Prev by Date: Re: Thickness of Lines and Arcs
  • Previous by thread: Re: Zero does not equal Zero
  • Next by thread: Additional Mathematica Style Sheets