Monday, November 9, 2009

Does Inheritance breaks Encapsulation?

Because inheritance exposes a subclass to details of its parent's implementation, it's often said that 'inheritance breaks encapsulation' (Gang of Four 1995:19)

No I did not read the GoF book, I'm quoting them because I believe quoting important people makes my point more correct.

So we know that inheritance breaks encapsulation because it exposes a subclass to details of its parent's implementation. But what is the harm of exposing parent's implementation to subclasses? Why does it matter?

Imagine this situation: you are coding a very core class for a system, and decided to make a field protected so it's convenient for subclasses to access it. After all, it is a core member field that all subclasses need to use and declaring it as protected seemed like reasonable thing to do. Everything worked fine and smoothly in the beginning. Then 5 years passed, assuming the system is actually making money for your company, it has grown substantially through a steady stream of feature requests. And many subclasses were created inheriting the core class you wrote. Now imagine you have to change that protected field, and *bam*, you're stuck! Because there are many subclasses sprang across many assemblies, and nobody has a headcount of them all! So you either end up not changing it, or do the change and fix as many subclasses as possible, then prey you don't miss any.

Does this sound familiar? Yes, this is the exact scenario when someone accidentally declared a field public for convenience when it should have been properly encapsulated, I hope it's not you, oops! (I'll be honest, I did this before!)

I believe this is the context when those influential people declared that inheritance breaks encapsulation. But a class does not have to expose its implementation to subclasses, take Hashtable for example: it is carefully designed to hide all implementation details from not just the rest of the world, but also its subclasses. So if there is a change to the default hashing method, how data is stored internally or any of the implementation details, all the subclasses created by developers across the world will not be broken! I believe a more proper statement would be: