Composition vs Inheritance
Low-Level Design: lesson 3 of 10
Assemble behaviour from parts instead of freezing it in a family tree.
Lesson 3 of 10 · 5 min
Composition vs Inheritance
Step 1 of 12
Inheritance says a child is its parent — decided once, at import time.
The Idea
Inheritance says a child is its parent, forever, decided at import time. Composition says an object has parts it can call, chosen when you build it — or later. Prefer composition: parts recombine, and a change to one part does not ripple through a family of subclasses.
Real-World Example
A camera rig versus a camcorder. The rig is a body, a lens, a gimbal and a mic that clip together, so a low-light shoot swaps one piece. The camcorder decided all four at the factory, and the only upgrade is a new camcorder.
The Code
class Belt:
def apply(self, item): return item + " +moved"
class Stamper:
def apply(self, item): return item + " +stamped"
class Line: # HAS-A list of stages; it IS-A nothing
def __init__(self, *stages): self.stages = list(stages)
def run(self, item):
for s in self.stages: item = s.apply(item)
return item
line = Line(Belt())
print(line.run("blank")) # blank +moved
line.stages.append(Stamper()) # new behaviour at runtime, no subclass
print(line.run("blank")) # blank +moved +stamped
Your turn
Fill in the blank.
class Wrapper:
def apply(self, item): return "[" + item + "]"
class Line:
def __init__(self, *stages): self.stages = list(stages)
def run(self, item):
for s in self.stages: item = ___
return item
print(Line(Wrapper(), Wrapper()).run("x")) # should print [[x]]Mini quiz
1 / 3