When?
1- 1- Behavior changes with state
Example:
switch(operation){
case “register”
register();
case “unregister”:
unregister();
case “update”
update();
}
Instead create a hierarchy with operation as a base class and register, unregister and update etc as subclasses. Now the instantiation of appropriate subclass lies on dependency injector or factory method
2- 2- Same check throughout the code
Example:
if(!isProduction){
logger.write(“something”)
}
Instead create a logger hierarchy with Logger as abstract class and NullLogger that does nothing.
So you do:
logger.write(“something”)
In this case the conditional checking required to instantiate a correct logger goes in logger factory or dependency injection.
Logger logger = LogFactory.getLogger();
getLogger(){
if(isProduction) return new NullLogger();
else return new FileLogger();
}
Benefits?
1- 1- Must for libraries so that others can extend and add their own behaviors
2- 2- Ease of testability, lesser code coverage tests.
3- 3- Readability