如何按父键下多键值列表的条目总数对Python Dictionary进行排序
Problem Overview
You have a nested dictionary where each top-level key (like London, Manchester) maps to a dictionary of shops, and each shop has a list of dictionary entries. You want to sort these top-level keys in descending order based on the total number of dictionary entries across all shops in each city.
Your sample data:
original_data = { "data": { "London": { "SHOP 1": [ {"kittens": 10, "type": "fluffy"}, {"puppies": 11, "type": "squidgy"} ], "SHOP 2": [ {"kittens": 15, "type": "fluffy"}, {"puppies": 3, "type": "squidgy"}, {"fishes": 132, "type": "floaty"} ] }, "Manchester": { "SHOP 1": [ {"kittens": 10, "type": "fluffy"}, {"puppies": 11, "type": "squidgy"} ], "SHOP 2": [ {"kittens": 15, "type": "fluffy"}, {"puppies": 3, "type": "squidgy"}, {"fishes": 132, "type": "floaty"} ], "SHOP 3": [ {"kittens": 15, "type": "fluffy"}, {"puppies": 3, "type": "squidgy"} ] }, "Edinburgh": { "SHOP 1": [ {"kittens": 10, "type": "fluffy"}, {"puppies": 11, "type": "squidgy"} ], "SHOP 2": [ {"kittens": 15, "type": "fluffy"} ], "SHOP 3": [ {"puppies": 3, "type": "squidgy"} ] } } }
As you noted, the totals are:
- London: 5 entries (2+3)
- Manchester:7 entries (2+3+2)
- Edinburgh:4 entries (2+1+1)
Desired sorted order: Manchester → London → Edinburgh
Solution
Your existing dictionary comprehension approach is on the right track—we just need to adjust the key function in sorted() to calculate the total number of entries for each city.
Here's the working code:
# Extract the inner data dictionary we want to sort cities_data = original_data["data"] # Sort the cities by total entries (descending order) sorted_cities = { city: shops for city, shops in sorted( cities_data.items(), key=lambda item: sum(len(entries) for entries in item[1].values()), reverse=True ) } # Update the original data with sorted cities (optional) original_data["data"] = sorted_cities # Print the result to verify print(sorted_cities)
How It Works
Let's break down the key parts:
cities_data = original_data["data"]: We first grab the inner dictionary containing the city-shop mappings—this is what we'll sort.- The
keyfunction:lambda item: sum(len(entries) for entries in item[1].values())item[1]is the dictionary of shops for a given city (e.g., London's shops)item[1].values()gives us all the lists of entries for each shop in the city- We loop through each list, get its length (number of dictionary entries), and sum those lengths to get the total for the city
reverse=True: This sorts the cities from highest total entries to lowest, matching your desired order.
Output Verification
When you run the code, the sorted dictionary will look like this (formatted for readability):
{ "Manchester": { "SHOP 1": [{"kittens": 10, "type": "fluffy"}, {"puppies": 11, "type": "squidgy"}], "SHOP 2": [{"kittens": 15, "type": "fluffy"}, {"puppies": 3, "type": "squidgy"}, {"fishes": 132, "type": "floaty"}], "SHOP 3": [{"kittens": 15, "type": "fluffy"}, {"puppies": 3, "type": "squidgy"}] }, "London": { "SHOP 1": [{"kittens": 10, "type": "fluffy"}, {"puppies": 11, "type": "squidgy"}], "SHOP 2": [{"kittens": 15, "type": "fluffy"}, {"puppies": 3, "type": "squidgy"}, {"fishes": 132, "type": "floaty"}] }, "Edinburgh": { "SHOP 1": [{"kittens": 10, "type": "fluffy"}, {"puppies": 11, "type": "squidgy"}], "SHOP 2": [{"kittens": 15, "type": "fluffy"}], "SHOP 3": [{"puppies": 3, "type": "squidgy"}] } }
This matches your expected order perfectly.
内容的提问来源于stack exchange,提问作者AlexW

