How to return all the minimum indices in numpy

Question:

I am a little bit confused reading the documentation of argmin function in numpy.
It looks like it should do the job:

Reading this

Return the indices of the minimum values along an axis.

I might assume that

np.argmin([5, 3, 2, 1, 1, 1, 6, 1])

will return an array of all indices: which will be [3, 4, 5, 7]

But instead of this it returns only 3. Where is the catch, or what should I do to get my result?

Asked By: Salvador Dali

||

Answers:

See the documentation for numpy.argmax (which is referred to by the docs for numpy.argmin):

In case of multiple occurrences of the maximum values, the indices corresponding to the first occurrence are returned.

The phrasing of the documentation (“indices” instead of “index”) refers to the multidimensional case when axis is provided.

So, you can’t do it with np.argmin. Instead, this will work:

np.where(arr == arr.min())
Answered By: nneonneo

That documentation makes more sense when you think about multidimensional arrays.

>>> x = numpy.array([[0, 1],
...                  [3, 2]])
>>> x.argmin(axis=0)
array([0, 0])
>>> x.argmin(axis=1)
array([0, 1])

With an axis specified, argmin takes one-dimensional subarrays along the given axis and returns the first index of each subarray’s minimum value. It doesn’t return all indices of a single minimum value.

To get all indices of the minimum value, you could do

numpy.where(x == x.min())
Answered By: user2357112

Assuming that you want the indices of a list, not a numpy array, try

import numpy as np

my_list = [5, 3, 2, 1, 1, 1, 6, 1]
np.where(np.array(my_list) == min(my_list))[0]

The index [0] is because numpy returns a tuple of your answer and nothing (answer as a numpy array). Don’t ask me why.

Answered By: grofte

I would like to quickly add that as user grofte mentioned, np.where returns a tuple and it states that it is a shorthand for nonzero which has a corresponding method flatnonzero which returns an array directly.

So, the cleanest version seems to be

my_list = np.array([5, 3, 2, 1, 1, 1, 6, 1])
np.flatnonzero(my_list == my_list.min())
=> array([3, 4, 5, 7])
Answered By: Luksurious

Recommended way (by numpy documents) to get all indices of the minimum value is:

x = np.array([5, 3, 2, 1, 1, 1, 6, 1])
a, = np.nonzero(x == x.min())  # a=>array([3, 4, 5, 7])
Answered By: Youjun Hu
Categories: questions Tags: ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.