Skip to content

S3Q1 · Shopping List

⚡ Quick Reference

Function: process_grocery_list(grocery_list: list, request: str)

def process_grocery_list(grocery_list: list, request: str):
    if request == "total_bill_amount":
        return sum(item["price"] * item["quantity"] for item in grocery_list)

    if request == "max_quantity_item":
        return max(grocery_list, key=lambda item: item["quantity"])["name"]

    if request == "sort_by_total_amount":
        return sorted(grocery_list,
                      key=lambda item: (-item["price"] * item["quantity"],
                                        item["name"]))

Key rules: - total_bill_amount → sum of price × quantity for all items - max_quantity_item → name of item with highest quantity; ties → first occurrence - sort_by_total_amount → descending by price × quantity; ties → ascending by name


Problem Statement

Problem

Write a function process_grocery_list(grocery_list, request) that handles three operations on a list of {name, quantity, price} dictionaries.

Sample data:

grocery_list = [
    {"name": "apple",  "quantity": 2, "price": 3},
    {"name": "banana", "quantity": 5, "price": 2},
    {"name": "carrot", "quantity": 4, "price": 1},
]

Expected outputs:

process_grocery_list(grocery_list, "total_bill_amount")
# → 20   (2×3 + 5×2 + 4×1 = 6 + 10 + 4)

process_grocery_list(grocery_list, "max_quantity_item")
# → "banana"   (quantity 5 is the highest)

process_grocery_list(grocery_list, "sort_by_total_amount")
# → [banana(10), apple(6), carrot(4)]


Operation 1 - total_bill_amount

Sum price × quantity across all items:

return sum(item["price"] * item["quantity"] for item in grocery_list)

From sample: (3×2) + (2×5) + (1×4) = 6 + 10 + 4 = 20


Operation 2 - max_quantity_item

Find the item with the highest quantity and return its name. Ties → first occurrence.

return max(grocery_list, key=lambda item: item["quantity"])["name"]

max() scans left to right and only updates on strictly greater - ties naturally return the first occurrence. From sample: banana(5) > carrot(4) > apple(2) → "banana"


Operation 3 - sort_by_total_amount

Sort by total amount descending, name ascending on ties:

return sorted(grocery_list,
              key=lambda item: (-item["price"] * item["quantity"],
                                item["name"]))

The tuple key (-total, name): - -total → negated so sorted() (ascending) gives descending total order - name → alphabetical tiebreaker

From sample: banana(10) > apple(6) > carrot(4) → [banana, apple, carrot]


Complete solution approaches

def process_grocery_list(grocery_list: list, request: str):
    if request == "total_bill_amount":
        return sum(item["price"] * item["quantity"] for item in grocery_list)

    if request == "max_quantity_item":
        return max(grocery_list, key=lambda item: item["quantity"])["name"]

    if request == "sort_by_total_amount":
        return sorted(grocery_list,
                      key=lambda item: (-item["price"] * item["quantity"],
                                        item["name"]))
def process_grocery_list(grocery_list: list, request: str):
    if request == "total_bill_amount":
        total = 0
        for item in grocery_list:
            total += item["price"] * item["quantity"]
        return total

    if request == "max_quantity_item":
        max_item = grocery_list[0]
        for item in grocery_list[1:]:
            if item["quantity"] > max_item["quantity"]:
                max_item = item
        return max_item["name"]

    if request == "sort_by_total_amount":
        def sort_key(item):
            total = item["price"] * item["quantity"]
            return (-total, item["name"])
        return sorted(grocery_list, key=sort_key)
def process_grocery_list(grocery_list: list, request: str):
    total = lambda item: item["price"] * item["quantity"]

    ops = {
        "total_bill_amount":  lambda gl: sum(total(i) for i in gl),
        "max_quantity_item":  lambda gl: max(gl, key=lambda i: i["quantity"])["name"],
        "sort_by_total_amount": lambda gl: sorted(gl, key=lambda i: (-total(i), i["name"])),
    }
    return ops[request](grocery_list)

Each operation is stored as a lambda - ops[request] selects the right one and calls it. Clean and extensible if more operations are added later.


Key takeaways

01

Negate total for descending sort

sorted() always sorts ascending. Using -total as the first element of the key tuple flips the order - the item with the highest total gets the smallest key and sorts first.

02

Tuple key for multi-criteria sorting

key=lambda i: (-total, name) sorts by two criteria in one pass. Python compares tuples lexicographically - the first element breaks most ties; the second handles the rest.

03

max() first-occurrence tie-breaking

max() scans left to right and only replaces the current best on strictly greater values. For tied quantities, the item that appeared first in the list is returned - no extra logic needed.