Decimals and other numbers

Steven D'Aprano steve+comp.lang.python at pearwood.info
Fri Jan 9 03:49:21 EST 2015


Devin Jeanpierre wrote:

> On Thu, Jan 8, 2015 at 6:43 PM, Dave Angel <davea at davea.name> wrote:
>> What you don't say is which behavior you actually expected.  Since 0**0
>> is undefined mathematically, I'd expect either an exception or a NAN
>> result.
> 
> It can be undefined, if you choose for it to be. You can also choose
> to not define 0**1, of course. 

No you can't -- that would make arithmetic inconsistent. 0**1 is perfectly
well defined as 0 however you look at it:

lim of x -> 0 of x**1 = 0
lim of y -> 1 of 0**y = 0


> If 0**0 is defined, it must be 1. I 
> Googled around to find a mathematician to back me up, here:
> http://arxiv.org/abs/math/9205211 (page 6, "ripples").

Not quite. I agree that, *generally speaking* having 0**0 equal 1 is the
right answer, or at least *a* right answer, but not always. It depends on
how you get to 0**0...

Since you can get difference results depending on the method you use to
calculate it, the "technically correct" result is that 0**0 is
indeterminate. But that's not terribly useful, and mathematicians with a
pragmatic bent (i.e. most of them) define 0**0 == 1 on the basis that it is
justifiable and useful, while 0**0 = 0 is justifiable but not useful and
leaving it as indeterminate is just a pain.

One argument comes from taking limits of x**y. If you set x to zero, and
take the limit as y approaches 1, you get:

lim of y -> 0 of 0**y = 0

But if you set y to 0, and take the limit as x approaches 0, you get:

lim of x -> 0 of x**0 = 1

There is a discontinuity in the graph of x**y, and no matter what value you
define 0**0 as, you cannot get rid of that discontinuity. Hence
indeterminate.

Here's another argument for keeping it indeterminate. Suppose we let 0**0 =
some value Q. Let's take the logarithm of Q.

log(Q) = log (0**0)

But log (a**b) = b*log(a), so:

log(Q) = 0*log(0)

What's log(0)? If we take the limit from above, we get log(x) -> -infinity.
If we take the limit from below, we get a complex infinity, so let's ignore
the limit from below and informally write:

log(Q) = 0*-inf

What is zero times infinity? In the real number system, that is
indeterminate, again because it depends on how you calculate it: naively it
sounds like it should be 0, but infinity is pretty big and if you add up
enough zeroes in the right way you can actually get something non-zero.
There's no one right answer. So if the log of Q is indeterminate, then so
must be Q.

But there are a host of good reasons for preferring 0**0 = 1. Donald Knuth
writes (using ^ for power):

    Some textbooks leave the quantity 0^0 undefined, because the 
    functions 0^x and x^0 have different limiting values when x 
    decreases to 0. But this is a mistake. We must define x^0=1 
    for all x , if the binomial theorem is to be valid when x=0, 
    y=0, and/or x=-y. The theorem is too important to be arbitrarily
    restricted! By contrast, the function 0^x is quite unimportant.

More discussion here:

http://mathforum.org/dr.math/faq/faq.0.to.0.power.html


> I expected 1, nan, or an exception, but more importantly, I expected
> it to be the same for floats and decimals.

Arguably, *integer* 0**0 could be zero, on the basis that you can't take
limits of integer-valued quantities, and zero times itself zero times
surely has to be zero.

But in practice, I agree that 0**0 should give the same result regardless of
the type of zeroes used, and if the result is a number rather than a NAN or
an exception, it should be 1.




-- 
Steven




More information about the Python-list mailing list