14

So say I have a list like:

my_list = [12, 13, 51, 21, 22, 58, 45.1, 34.2, 56, 6, 58, 58] 

So the max number in this is obviously 58, but I don't just want to return one 58, I want a list of all the indexes that have that max number.

Basically for this I want the result [5, 10, 11]

I know that if I want the max number I can do my_list.index(max(my_list)) but that will simply give me the first index.

Any tips? Also, I want to stick to simple methods such as sort, max, len, etc...

jonrsharpe
  • 115,751
  • 26
  • 228
  • 437
user3324536
  • 325
  • 1
  • 6
  • 13
  • See also [`more_itertools.locate()`](https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.locate) – pylang Aug 02 '19 at 20:25
  • Does this answer your question? [How to find all positions of the maximum value in a list?](https://stackoverflow.com/questions/3989016/how-to-find-all-positions-of-the-maximum-value-in-a-list) – Georgy Apr 22 '21 at 08:46

4 Answers4

23

You can determine the maxval with max:

maxval = max(my_list)

Then get the indices using enumerate and a list comprehension:

indices = [index for index, val in enumerate(my_list) if val == maxval]

For your example, I get

maxval == 58
indices = [5, 10, 11]

As per Keyser's suggestion, you could save iterating over the list twice (once to determine maxval, once to find matching indexes) by doing:

maxval = None
for index, val in enumerate(my_list):
    if maxval is None or val > maxval:
        indices = [index]
        maxval = val
    elif val == maxval:
        indices.append(index)
jonrsharpe
  • 115,751
  • 26
  • 228
  • 437
  • 2
    Or, to replace runtime with some memory, traverse the list once and keep track of the indices of the biggest so far, somehow. I don't have anything pythonic. – keyser Feb 18 '14 at 18:08
  • Nice one. Definitely +1 – keyser Feb 18 '14 at 18:13
  • Slight but important error in your second example: it needs to append `index` to `indices`, not `val`... Also, I don't think all the overhead makes it worth saving that extra iteration. For a short list, the list comprehension version is twice as fast as the `elif` method, and for a longer list it was 4x faster. – beroe Apr 30 '14 at 23:49
  • it is failing if the list has negative values in it..@jonrsharpe – Achy97 Mar 25 '19 at 09:09
  • @Achy97 as far as I can tell it works fine with negative values. For example if I run with `my_list = [12, 13, 51, 21, -22, 58, 45.1, 34.2, -56, 6, 58, 58]` I still get `[5, 10, 11]`. It's unclear what your specific problem is. – jonrsharpe Mar 25 '19 at 09:49
1

Similar to enumerate and list comprehension, you can also use filter:

maxval = max(my_list)
indices = list(filter(lambda x: my_list[x]==maxval, list(range(len(my_list)))))
Andi Zhang
  • 11
  • 1
0

I tried to do the most Pythonic way as possible

my_list = [12, 13, 51, 21, 22, 58, 45.1, 34.2, 56, 6, 58, 58] 
max_indices = [i for i in range(len(my_list)) if my_list[i] == max(my_list)]

Edit: Ashwini is right. max() needs to be outside the list, so...

max_value = max(my_list)
max_indices = [i for i in range(len(my_list)) if my_list[i] == max_value]
ysakamoto
  • 2,512
  • 1
  • 16
  • 22
-1

Enumerate will help you to get the value and location

maxx = max(my_list)
for i,j in enumerate(my_list):
    if j == maxx:
        print i,j

output

5 58

10 58

11 58

rajpython
  • 179
  • 2
  • 3
  • 14