Tuesday, August 28, 2012

A better way to solve Refused Bequest

There is a bad smell called Refused Bequest, which means subclasses don't want or need what they are given by superclass. According to Refactoring: Improving the Design of Existing Code (by Martin Fowler, Kent Beck, John Brant, William Opdyke, Don Roberts p.87), there are two ways to solve it. Traditional way is to create a new sibling class and use Push Down Method and Push Down Field to push all the unused methods to the sibling. Or use Replace Inheritance with Delegation, if the subclass does not want to support the interface of the superclass.

I have to say I'm shocked by how easily this expression could mislead those less experienced developers. How come bad smells in code can be solved like taking OTC medicines without even asking readers to focus on their software design.

Let me start with the 2nd solution. If there is no is-a relationship, there shouldn't be a class hierarchy. That said, removing a hierarchy should only be supported by the evidence that the original is-a relationship is not valid any more. By removing the hierarchy, two classes can only interact with each other in OO way - sending messages. This is the point. Readers shouldn't be misled that delegation can be used to remove inheritance.

The 1st solution has potential problems in any working system. Pushing method / field from parent to newly created sibling, just because a subclass in the inheritance tree doesn't want the method / field? This definitely breaks the contract between parent class and the rest of the world. A more engineering way is introducing a new base class, moving all the methods / fields the subclass wants from original base class to new base class and making both the subclass and the original base class extend new base class. Again, problem is solved by applying OO design, not by taking OTC medicines.



I'm not saying identifying bad smells and refactoring to solve them are of no values. I just want to highlight that bad smell comes from bad (or outdated) design, and can only be solved by good (or updated) design. Remember, refactoring with books at hand but nothing in mind is also a bad smell.