Reading programming books:`Head First Design Patterns`
Recently, I have finished reading ‘Head First Design Patterns’. Here I summarize some of the extremely fundamental points that I contemplated to keep them in mind.
1. Don’t make class big, make it small and composable
This is same as ‘Favor composition over inheritance’. Simply speaking, when creating abstract class, don’t define too many things in the abstract class. For example, when creating the duck class, any kind of behaviors like swim, fly, quack can be varied depending on duck type. Instead of defining all those behaviors in the duck abstract class at a time(inheritance), create each separate interface for swim, fly, quack and compose those interfaces into the duck, which will make your code much more flexible. Moreover, those interfaces can be composed into and implemented by any kinds of classes which do swim, fly, walk and quack such as animals and humans. This is kind of similar concept to the functional programming which does not fix behaviors to a particular object and create each behavior separately, eventually those behaviors are connected by function pipeline (not by method chains) regardless of object types.
2. Abstract class as much as possible
This is same as ‘Program to an interface not an implementation’. The concept is very simple like example below (quoted from the book). Dog is abstracted to Animal.
Programming to an implementation
Dog d = new Dog();
Programming to an interface/supertype
Animal animal = new Dog();
If we do not comply with this principle, we will run into a lot of if else statements and instance type checking. If there are too many if else statement and instance type checking in the code, a reasonable doubt should be raised and the appropriate remedy has to be taken.
3. Increase the cohesion
This is same as ‘A class should have only one reason to change’, which represents the most famous programming principle, a single responsibility. Cohesion is a measurement of how much focused a single class is on a single responsibility. The very simple example is that we strictly separate error handling and logging logic from a featured class.
Followings are some of the design patterns applied in Angular.
1. Decorator (Decorator pattern)
Decorator pattern is used for adding additional functionalities to an object dynamically. A decorator has to have the same type as the object (component) they are going to decorate (wrap). Here, the component is not same as the (web) component in Angular. In Decorator pattern, the top super class is referred to as a component. Angular framework has a multiple built-in decorators, one of them is @component decorator, which transforms our normal class to a (web) Angular component.
2. LifeCycle Hooks (Template pattern)
Template pattern defines the algorithm steps in a abstract class and allows subclasses to implement those steps. Especially, a hook is a method that is declared in the abstract class as empty or default. This gives subclasses to ability to hook into a relevant step if it is necessary. Of course, it is totally okay if it remains empty. In Angular component, there are several lifecycle hooks we can implement on our own. For an angular component to perform its task, there are a series of steps in sequence, such as ngOnInit, ngAfterContentInit, ngAfterViewInit, ngOnDestroy. Angular framework gives us an ability to hook into the angular component lifecyle by implementing those methods.
3. Reactive form (Composite pattern)
Composite pattern composes objects into tree structures which can contain both composite and individual objects. For instance, a file system is represented as a tree structure which contains both directory (composite object) and file (individual object). The composite object (node) can have both another composite object and a individual object (leaf) as a child. Composite pattern treats those individual and composite objects uniformly so that we can ignore the differences between them by implementing a same superclass. In Angular reactive form, there are two important form elements, formgroup and formcontrol. The formgroup can have a formgroup itself and a formcontrol as a child. Actually, angular application itself is a tree structure composed of leaf components and node components.