Skip to content Skip to sidebar Skip to footer

Numpy.reciprocal Returns Different Values When Called Repeatedly

I have a numpy array ssh_sum: >>> ssh_sum array([[ 0., 2., 1., 0., 0., 0.], [ 0., 0., 1., 2., 0., 0.], [ 0., 0., 0., 1., 0., 2.]]) I wanted t

Solution 1:

It is not just reciprocal; the issue occurs with any use of the where argument. I've been able to reproduce the issue with the master branch of numpy (np.__version__ is '1.15.0.dev0+c093997'), with functions such as abs, sign, add, subtract, etc.

If you read the docstrings of the numpy "ufuncs" carefully and interpret them correctly, you'll see that the behavior is not a bug. Here are the relevant descriptions from the numpy.reciprocal docstring:

out : ndarray, None, or tuple of ndarray andNone, optional
    A location into which the resultis stored. If provided, it must have
    a shape that the inputs broadcast to. If not provided or `None`,
    a freshly-allocated arrayis returned. A tuple (possible onlyas a
    keyword argument) must have length equal to the number of outputs.
where : array_like, optional
    ValuesofTrue indicate to calculate the ufunc at that position, valuesofFalse indicate to leave the valuein the output alone.

Note, in particular:

  • where says "values of False indicate to leave the value in the output alone."
  • out says "If not provided or None, a freshly-allocated array is returned."

You did not provide an out argument, so a new array is allocated by your call to reciprocal. The contents of this array are not initialized; the array holds whatever happened to be in the allocated memory. When you use the where argument, only those positions in the output where where is True are assigned values. Positions where where is False are not touched, so they hold whatever random stuff was there when the array was allocated. For floating point output, the random stuff in the output might be 0.0, 4.85105226e-309, or any other random values.

To use the where argument the way you intended, you should also provide your own out argument, initialized with the values you want in the output where where is False. In your case, you should pass in an array of zeros:

In [84]: ssh_sum
Out[84]: 
array([[0., 2., 1., 0., 0., 0.],
       [0., 0., 1., 2., 0., 0.],
       [0., 0., 0., 1., 0., 2.]])

In [85]: out = np.zeros_like(ssh_sum)

In [86]: np.reciprocal(ssh_sum, where=ssh_sum > 0.0, out=out)
Out[86]: 
array([[0. , 0.5, 1. , 0. , 0. , 0. ],
       [0. , 0. , 1. , 0.5, 0. , 0. ],
       [0. , 0. , 0. , 1. , 0. , 0.5]])

In [87]: out
Out[87]: 
array([[0. , 0.5, 1. , 0. , 0. , 0. ],
       [0. , 0. , 1. , 0.5, 0. , 0. ],
       [0. , 0. , 0. , 1. , 0. , 0.5]])

Post a Comment for "Numpy.reciprocal Returns Different Values When Called Repeatedly"