In software design, sometimes you are faced with design decisions where the two options seem equally good. Certainly the decision to go with an Abstract Class or to use an Interface falls into this category. In the following article I hope to present a few tips to resolve this design dilemma.
- Cannot be instantiated.
- Can have implementation for some or all the abstract methods. Ofcourse, the child classes can override the behavior.
- Can declare private, protected and public methods and members.
- A class can inherit from only one abstract class.
- Cannot be instantiated
- Cannot have implementation. Sometimes, constants are defined (with ‘final’ keyword)
- Everything is public.
- A class can implement any number of interfaces.
Now it is time for design decision! What will you choose? Abstract class becomes part of the class-hierarchy. Interface is just a contract that the implementing class has to obey. The classes which form a class-hierarchy are related very strongly. They obey ‘is-a’ relationship. ‘Toyota Camry’ is-a car and ‘Chevy Volt’ is-a car. In this case ‘Car’ can be an abstract class. A ‘house’ and a ‘car’ can be painted. But this quality of being able to be painted is not as strong. So ‘Paintable’ can be an interface.
First tip is do not be under any pressure to use abstract classes. Use abstract classes only when appropriate. Initially the quality of being 'paintable' seems to qualify for an abstract class. Upon deeper analysis you will conclude that it is an interface. Think about the quality of being 'Washable'? Both 'Home' and 'Car' are washable. Now you know that in Java a child-class can be derived only from one abstract class. Both 'Paintable' and 'Washable' seem equally important. When you find multiple qualities, at the same level or priority, that qualify for an 'is-a' relationship you realize that they are not candidates for being abstract classes.
Second tip is that abstract classes allow you to partially implement your class. Use this to your advantage and provide some default behavior in the base methods which can be daisy-chained or overridden in the child-classes.