2.2.5 · Coding › Design Principles
Intuition Ek sentence mein idea
==Software entities (classes, modules, functions) extension ke liye open honi chahiye lekin modification ke liye closed .==
Matlab: tum naya behavior add kar sako naya code likhke , na ki already kaam karte code ko edit karke .
Intuition Yeh principle kyun zaroori hai
Jab bhi tum existing, tested code ko edit karte ho , tum risk lete ho:
Kuch jo pehle se kaam kar raha tha woh tod do (regression).
Poori file ko phir se test karo, redeploy karo, re-review karo.
Ek aisi class ko touch karo jis par kaafi unrelated teams depend karti hain.
Agar tum ek naya file/class add karke naya behavior introduce kar sako, toh purana code frozen, tested, aur trusted rehta hai. Change additive banta hai, invasive nahi. Yahi poora fayda hai: jo kaam karta hai uski stability + jo naya hai uske liye flexibility.
Definition Extension ke liye open
Module ka behavior extend kiya ja sakta hai — jaise requirements badhti hain, tum use naye kaam karwa sakte ho.
Definition Modification ke liye closed
Naya behavior add karne ke liye existing module ka source code nahi badla jata . Uska .cpp/.java/.py file untouched rehta hai.
Intuition Yeh dono ek saath kaise ho sakta hai? (apparent paradox)
Yeh contradictory lagta hai: code change kiye bina behavior kaise badalte ho? Trick hai ==abstraction ==. Tum ek stable interface (abstraction) par depend karte ho, aur us interface ke peeche naye implementations swap in / add karte ho. Abstraction "frozen contract" hai; implementations "extension points" hain.
Core enablers hain polymorphism aur Dependency Inversion ki aadat:
Code ka woh part dhundo jo vary karta hai (woh cheez jo tumhe baar baar switch/if-else edit karwati hai).
Us variation ko ek abstract interface ke peeche chhupa do.
High-level code ko interface par dependent banao, concrete types par nahi.
Naya requirement → ek naya class likho jo interface implement kare. Purana code kabhi nahi khulta.
Worked example ❌ OCP ka violation
class AreaCalculator :
def area (self, shape):
if shape.type == "circle" :
return 3.14159 * shape.r ** 2
elif shape.type == "rectangle" :
return shape.w * shape.h
# Triangle add karna? → is method ko PHIR SE EDIT karna padega 😖
Yeh bura kyun hai? Har naya shape tumhe area() ko reopen aur edit karne par majboor karta hai — ek kaam karta, tested method. if/elif chain woh variation point hai jo abstract hone ke liye chilla raha hai.
Worked example ✅ OCP follow karna
from abc import ABC , abstractmethod
class Shape ( ABC ):
@abstractmethod
def area (self): ...
class Circle ( Shape ):
def __init__ (self, r): self .r = r
def area (self): return 3.14159 * self .r ** 2 # Kyun? Circle apna formula khud jaanta hai
class Rectangle ( Shape ):
def __init__ (self, w, h): self .w, self .h = w, h
def area (self): return self .w * self .h
class AreaCalculator :
def total (self, shapes):
return sum (s.area() for s in shapes) # Kyun? Sirf Shape contract par depend karta hai
Yeh step (Shape ABC) kyun? Yeh contract freeze karta hai ki "har shape area() compute kar sakta hai."
Yeh step (AreaCalculator.total) kyun? Ab ise kabhi bhi zero edits ki zaroorat nahi — yeh sirf abstraction se baat karta hai.
Triangle add karna? Bas class Triangle(Shape) likho. ✅ Closed code untouched, naya behavior add ho gaya.
Worked example Requirement badhti rehti hai: regular, premium, seasonal... customers
class Discount ( ABC ):
@abstractmethod
def apply (self, price): ...
class NoDiscount ( Discount ):
def apply (self, price): return price
class PremiumDiscount ( Discount ):
def apply (self, price): return price * 0.80 # Kyun? 20% off YAHAN rehta hai
class SeasonalDiscount ( Discount ):
def __init__ (self, pct): self .pct = pct
def apply (self, price): return price * ( 1 - self .pct)
def checkout (price, discount: Discount): # Kyun? abstraction leta hai
return discount.apply(price)
Yeh OCP kyun hai: Naya "Black Friday 70% off" rule = ek naya class BlackFriday(Discount). checkout kabhi nahi badlega. Yeh Strategy pattern hai, OCP ka sabse common realization.
Common mistake "Main bas ek aur
if branch add kar lunga — yeh faster hai."
Kyun sahi lagta hai: Ek change ke liye genuinely faster hota hai — abstraction ka upfront cost hota hai.
Trap: 5th, 6th, 7th branch function ko ek fragile mega-method bana dete hain; har edit baaki sab existing cases ko risk mein dalta hai.
Fix: ==Rule of Three == apply karo: pehla if/else tolerate karo, lekin teesri variation par polymorphism ke liye refactor karo. Bahut jaldi abstract bhi mat karo (next dekho).
Common mistake Over-engineering: "just in case" har cheez ke liye ek interface.
Kyun sahi lagta hai: "OCP kehta hai extensible raho, toh main har class ko pluggable bana dunga!"
Trap: Ek-implementation interfaces ka phaad = needless indirection, padhna mushkil ho jata hai. OCP speculative-generality bait hai.
Fix: Abstraction sirf wahan add karo jahan actually change pehle hua ho (predicted variation), har jagah nahi.
Common mistake Sochna ki OCP saare changes forbid karta hai.
Kyun sahi lagta hai: "Closed for modification" absolute lagta hai.
Trap: Bug fixes ke liye code edit karna hi padta hai . OCP naye features/variations add karne ke baare mein hai, fixes ban karne ke baare mein nahi.
Fix: Ise aise padho: naye behavior ke liye existing well-factored modules ko modify nahi karna chahiye.
OCP ka full form aur yeh kya kehta hai Open/Closed Principle — software entities extension ke liye open aur modification ke liye closed honi chahiye.
"Open for extension" ka matlab kya hai Tum module mein naya behavior add kar sakte ho jaise requirements badhti hain.
"Closed for modification" ka matlab kya hai Tum woh behavior existing source code edit kiye bina add karte ho.
OCP ko possible banane ka key mechanism Abstraction + polymorphism — stable interface par depend karo, uske peeche naye implementations add karo.
OCP se sabse zyada associated design pattern Strategy pattern (aur Template Method / plugin architectures).
Type field par lamba if/elif ya switch kis violated principle ka smell hai Open/Closed Principle.
"Rule of Three" tumhe kya bolta hai Teesri variation par polymorphism ke liye refactor karo, pehle nahi (premature abstraction se bachao).
Kya OCP bug fixes forbid karta hai Nahi — yeh naya behavior add karne ko target karta hai; bugs fix karne ke liye abhi bhi code edit karna padta hai.
SOLID mein OCP kaun sa letter hai "O".
Naye Shape class ke andar kya jata hai vs AreaCalculator mein kya Shape ka apna area formula naye class mein jata hai; calculator sirf area() abstraction ko call karta hai.
Recall Feynman: 12 saal ke bacche ko samjhao
Socho tumhare paas ek toy robot hai jo tricks kar sakta hai. Abhi woh wave aur spin kar sakta hai. Tum chahte ho woh dance bhi kare. Bura tarika: robot ko kholkar uska brain rewire karo — ho sakta hai waving tod do. OCP tarika: robot mein slots hain jahan tum trick cards plug in kar sakte ho. Dancing add karne ke liye, bas ek naya "dance card" slide in karo . Robot ke andar kabhi nahi khulta. Purani tricks safe rehti hain, naye tricks add hote hain. Yahi hai "naye tricks ke liye open, andar kaat kar kholne ke liye closed."
"Add karo, edit mat karo." Ya: O ld code C losed rehta hai, naya code P lug in hota hai.
Ek wall socket socho: wall (closed) kabhi nahi badlti, tum bas naye devices plug in karte ho (extensions).
Editing tested code risks regression
Add new code not edit old
Depend on stable interface
Dependency Inversion habit
New requirement adds new class