Comparing lists with min() based on out of order comparisons

83 views Asked by At

I have a list of lists, for example q = [[1,2],[3,4]], where each sub-list is a list of 2 integers, and I return the index of each extreme point (I think?).

What I need is the index of the list with the min/max value in the second entry out of all the second entries of the sublists, and where there are other sublists with the same value in the second entry, the index with the min/max first value out of the list of min/max second value entries is returned.

For example, if q = [[1, 2], [3, 4], [1, 0], [0, 5]], and I need min second, if tie, then min second and then first. So I need min(S) to return [1,0]. Instead, what it seems to return is [0,5].

>>> q = [[1,2],[3,4]]
>>> min(q)
[1, 2]
>>> q.append([1,0])
>>> min(q)
[1, 0]
>>> q.append([0,5])
>>> min(q)
[0, 5]
>>> q
[[1, 2], [3, 4], [1, 0], [0, 5]]

According to this answer here, comparing lists compares them in order of the elements, using the next list entry for tie-breakers.

>>> q.append([0,6])
>>> q.append([0,4])
>>> min(q)
[0, 4]
>>> q
[[1, 2], [3, 4], [1, 0], [0, 5], [0, 6], [0, 4]]
>>> 

Is there some way I can control the ordering in the comparison? I tried reading through the documentation, but I don't understand what I'm reading.

3

There are 3 answers

2
maxymoo On BEST ANSWER

Does this work for you?

min(q, key = lambda x: (x[1],x[0]))
0
James Mills On

Use the key keyword argument of [min()](1]:

Example:

>>> from operator import itemgetter
>>> q = [[1, 2], [3, 4], [1, 0], [0, 5]]
>>> min(q, key=itemgetter(1, 0))
[1, 0]

This will sort the iterable q by the key function itemgetter(1, 0) which basically returns a tuple of (2nd-item, 1st-item) and is equivilent to min(q, key=lambda x: (x[1], x[0])).

min(iterable[, key]) min(arg1, arg2, *args[, key])\

Return the smallest item in an iterable or the smallest of two or more arguments.

If one positional argument is provided, iterable must be a non-empty iterable (such as a non-empty string, tuple or list). The smallest item in the iterable is returned. If two or more positional arguments are provided, the smallest of the positional arguments is returned.

The optional key argument specifies a one-argument ordering function like that used for list.sort(). The key argument, if supplied, must be in keyword form (for example, min(a,b,c,key=func)).

Changed in version 2.5: Added support for the optional key argument.

0
dawg On

You can use extended slice syntax to reverse the sub lists:

>>> q = [[1, 2], [3, 4], [1, 0], [0, 5]]
>>> min(q, key=lambda sl: sl[::-1])
[1, 0]