Numpy, divide by zero: two different results for the same operation

一曲冷凌霜 提交于 2019-12-12 09:15:48

问题


After having searched around a little bit, I'm still struggling with divisions by zero in numpy. I am stunned by the contradiction I report right away:

from numpy import *

seterr(all='ignore')    # Trying to avoid ZeroDivisionError, but unsuccessful.

def f(x) :
    return 1./(x-1.)

With this, when I execute f(1.), I get ZeroDivisionError: float division by zero.

However, when I define z = array( [ 1., 1. ] ) and execute f(z), I do not get any error, but array([ inf, inf]).

As you can see, there is kind of a contradiction between both outputs. My first question is why.

Ideally, I would like to get inf as the output of f(1.), or at least nan, but not an error (and therefore the stoppage of the calculation). My second question is how to manage this. Notice my failed attempt by making use of seterr.


回答1:


Numpy is not involved in your function f. You'll have to catch the ZeroDivisionError if you want to alter the output.

import numpy

def f(x) :
    try:
        return 1./(x-1.)
    except ZeroDivisionError:
        return numpy.nan

Or use numpy's division:

import numpy

def f(x) :
    return numpy.divide(1., (x-1.))

Or only pass numpy types to f:

import numpy

def f(x) :
    return 1./(x-1.)

x = numpy.float_(1)
print f(x) # prints inf



回答2:


1. is an ordinary Python float, and these raise exceptions instead of using nan/inf. When you call f(1.), numpy is not involved in any way. Just doing from numpy import * (or calling numpy functions like seterr) doesn't change anything about how ordinary Python types work; it will only affect operations on numpy objects, and you only get numpy objects if you explicitly create them.

When you do explicitly create a numpy object, as in your f(z) example, you involve numpy, which has its own types that differ from the basic Python types. Notably, numpy numeric types do use nan/inf.

As far as I know, there is no way to get plain Python floats to start returning nan or inf instead of raising exceptions, so you'll have to use numpy scalars instead of plain Python floats (as described in this question) if you want to support both scalar and vector operations.




回答3:


It looks like seterr is intended to be used with Numpy types; how could it be used with Python native type. On the other hand, if you do:

f(np.array((1,)))

No error should occur with your seterr.



来源:https://stackoverflow.com/questions/34664250/numpy-divide-by-zero-two-different-results-for-the-same-operation

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!