Reputation: 43
I have a Python sorting problem which is similar to other problems I found on stackoverflow, but not quite the same. Let me show you, maybe someone may help:
Assume that we have a list of lists which may look like this:
p = [[6, 'k'], [5, 'l'], [2, 'p'], [2, 'd'], [5, 'k']]
I want to sort this by two (!) criteria. Sorting it by one criterion is rather easy and straightforward. Let's assume I want to first sort it by the first item of each list. I could implement this as such:
sorted_p = sorted(p, key=lambda x:int(x[0]))
So far so good. I would get the following sorted_p:
[[2,'p'], [2, 'd'], [5, 'l'], [5, 'k'], [6, 'k']]
Now the real trouble starts: I want that in every case where there are multiple occurrences of the first item (e.g. we have two tuples starting with 2 and two tuples starting with 5) that these tuples are then sorted by the second item of the tuple. So what I would like to get as a result would be
[[2,'d'], [2, 'p'], [5, 'k'], [5, 'l'], [6, 'k']]
Has anyone an idea how I can do that?
Thanks for every hint!
Upvotes: 0
Views: 1529
Reputation: 3110
I think this version using operator.itemgetter
reads better than the lambda
version:
import operator
p = [[6, 'k'], [5, 'l'], [2, 'p'], [2, 'd'], [5, 'k']]
sorted_p = sorted(p, key=operator.itemgetter(0, 1))
Upvotes: 1
Reputation: 2195
The accepted answer is great. Just adding another answer without using the built-in sort in case of customizations it can be extended.
def custom_bubble_sort(arr):
for i in range(len(arr)-1):
for j in range(len(arr)-i-1):
if arr[j][0] > arr[j+1][0]:
temp = arr[j]
arr[j] = arr[j+1]
arr[j+1] = temp
elif arr[j][0] == arr[j+1][0] and ord(arr[j][1]) > ord(arr[j+1][1]):
temp = arr[j]
arr[j] = arr[j+1]
arr[j+1] = temp
return arr
print(custom_bubble_sort([[6, 'k'], [5, 'l'], [2, 'p'], [2, 'd'], [5, 'k']]))
Upvotes: 1
Reputation: 627
Python automatically sorts by more than 1 criteria if you pass it a tuple. In your case it would be:
p = [[6, 'k'], [5, 'l'], [2, 'p'], [2, 'd'], [5, 'k']]
sorted_p = sorted(p, key=lambda x:(int(x[0]),x[1]))
Upvotes: 5