3

If I have an NxN numpy array and if there is a negative number as any position, is there a simple and quick way I can replace that number with a 0? something like

for item in array:
    if item <= 0: 
        item = 0
StealthPython
  • 113
  • 1
  • 9
  • `array[array <= 0 ] = 0` should work also you say negative, shouldn't it be `array[array < 0] = 0` rather than `<=0`? – EdChum Dec 07 '16 at 14:44
  • @EdChum ... it doesn't make a difference, because you end up replacing `0` with `0`. The only difference might be if the array has `float`s and some `0` have the "negative sign" while other have the positive sign, by assigning `0` you set all of them to the "positive sign", but I believe all the operations should work the same. – Bakuriu Dec 07 '16 at 14:48
  • @Bakuriu true but there is a semantic difference here between `<0` and `<=0` with the negative statement irrespective of the end result, it's clear that `<0` means negative whilst `<=0` does not – EdChum Dec 07 '16 at 14:50
  • whats wrong with the code provided? (never used numpy so i might be asking a stupid question) – WhatsThePoint Dec 07 '16 at 14:50
  • @WhatsThePoint it's not vectorised and the most efficient method of setting the elements to 0, if you have a large array then you end up iterating over each row in this case whilst using a mask will set the entire array in a vectorised manner – EdChum Dec 07 '16 at 14:52
  • @EdChum cheers. – WhatsThePoint Dec 07 '16 at 14:53
  • @EdChum True in this case <0 is better than <=0, since I'm replacing with 0. Just a bad habit that i put <= at time. – StealthPython Dec 07 '16 at 14:54

2 Answers2

7

You can mask the entire array by using a boolean mask, this will be much more efficient than iterating like you currently are:

In [41]:
array = np.random.randn(5,3)
array

Out[41]:
array([[-1.09127791,  0.51328095, -0.0300959 ],
       [ 0.62483282, -0.78287353,  1.43825556],
       [ 0.09558515, -1.96982215, -0.58196525],
       [-1.23462258,  0.95510649, -0.76008193],
       [ 0.22431534, -0.36874234, -1.46494516]])

In [42]:
array[array < 0] = 0
array

Out[42]:
array([[ 0.        ,  0.51328095,  0.        ],
       [ 0.62483282,  0.        ,  1.43825556],
       [ 0.09558515,  0.        ,  0.        ],
       [ 0.        ,  0.95510649,  0.        ],
       [ 0.22431534,  0.        ,  0.        ]])
EdChum
  • 376,765
  • 198
  • 813
  • 562
2

Based on this SO answer, you can use numpy's builtin indexing for this.

arr[arr < 0] = 0
Community
  • 1
  • 1
lucasnadalutti
  • 5,818
  • 1
  • 28
  • 48
  • 1
    how is this answer different to mine? – EdChum Dec 07 '16 at 14:50
  • I hadn't seen your answer while posting mine. I won't remove mine since it adds something new which is a reference that contains explanation and benchmarking. Don't worry, though, I upvoted yours and I think it should be the selected answer for being the first one. – lucasnadalutti Dec 07 '16 at 14:55
  • I don't have an issue with duplicated answers so long as it adds something new, it would be better if you added the relevant parts to your answer rather than just a link, just an observation – EdChum Dec 07 '16 at 14:56