Dunder: Inventory

Dunder: Inventory

Write an Inventory class that supports Python's built-in len() and in directly.

Inventory()
  • __init__(self) — starts empty (an internal dict mapping item name to quantity).
  • add(self, name, qty) — adds qty of name to the inventory (accumulating if name already has some quantity).
  • __len__(self) — called automatically by len(inventory). Returns the number of distinct item names stored (not the total quantity).
  • __contains__(self, name) — called automatically by name in inventory. Returns True if name has been added.

Examples

inv = Inventory()
inv.add("apple", 3)
inv.add("banana", 2)
len(inv)              // → 2   (two distinct items)
"apple" in inv         // → True
"banana" in inv         // → True
"cherry" in inv          // → False

Walkthrough

Thinking it through

class Inventory:
    def __init__(self):
        self.items = {}

    def add(self, name, qty):
        self.items[name] = self.items.get(name, 0) + qty

    def __len__(self):
        return len(self.items)

    def __contains__(self, name):
        return name in self.items

add reuses the exact accumulator pattern from Word Frequency, back in the dictionaries section: .get(name, 0) + qty handles both a brand-new item (defaulting to 0) and an item that already has some quantity stored, adding to it either way.

__len__ and __contains__ are both thin wrappers around the internal dict's own built-in behavior — len(self.items) and name in self.items — which is a common and completely reasonable pattern for dunder methods: your class holds some underlying data structure (here, a dict) that already knows how to do the thing you want, and your dunder method just delegates to it.

The distinction worth noticing: len(inv) returns 2 for two distinct items even if inv.add("apple", 3) was called several times (adding more apples doesn't create a new distinct item) — that's exactly why __len__ returns len(self.items) (the number of dict keys), not the sum of all the quantities stored.

Once these dunder methods are defined, Inventory objects work with Python's built-in syntax exactly like a list or dict would — len(inv) and "apple" in inv — without anyone calling inv.__len__() or inv.__contains__("apple") directly.

main.py
Console
Press Run to execute your code, or Submit to test and complete this problem.