You already know how to sort a list of numbers or strings. But what if your data is more complex? What if each item has several fields, and you only care about one of them?
The key argument
Both
sorted() and the .sort() method accept a keyword called key. The value you pass to key is a function. Python calls that function once for every item in your list, uses the result as a temporary "label", sorts by those labels, but returns or keeps the original items.words = ['banana', 'kiwi', 'fig']
by_length = sorted(words, key=len)
print(by_length)Lambdas: tiny one-line functions
When the key function is simple, writing a full
def feels heavy. A lambda lets you define an anonymous inline function in one expression:last_char = lambda s: s[-1]
print(last_char('hello'))So
sorted(words, key=lambda w: len(w)) is exactly the same as using a named function that returns len(w). You will see this pattern everywhere.Sorting lists of dictionaries
players = [
{'name': 'Ada', 'score': 42},
{'name': 'Linus','score': 91},
{'name': 'Grace','score': 67}
]
top_players = sorted(players, key=lambda p: p['score'], reverse=True)
for p in top_players:
print(p)reverse=True flips the order. Without it you get ascending (smallest first). With it you get descending (largest first).Sorting by two fields at once
What if scores tie? You can return a tuple from your key function. Python compares tuples element-by-element, so the first value is primary and the second breaks ties.
players = [
{'name': 'Ada', 'score': 90},
{'name': 'Zoe', 'score': 75},
{'name': 'Ben', 'score': 90}
]
sorted_players = sorted(players, key=lambda p: (-p['score'], p['name']))
for p in sorted_players:
print(p)