s

SOLID Principles edit button Edit

author
Murugan Andezuthu Dharmaratnam | calendar 18 July 2022 | 597

Design Pattern vs Design Principle

First question when I started learning about SOLID principle was if SOLID principle a design pattern. The answer to that is NO. Design Principles are general guidelines that can guide your class structure and relationships. On the other hand, Design Patterns are proven solutions that solve commonly reoccurring problems.

5 Solid Principles

  1. Single Responsibility Principle
  2. Open Closed Principle
  3. Liskov Substation Principle
  4. Interface Segregation Principle
  5. Dependency Inversion Principle

Single Responsibility Principle

Single Responsibility Principle (SRP) states that a class should have only one responsibility or a class should have only one reason to change. In the book clean code Robert C Martin states that any module (set of functions, class, packages, source code) should have reason to change only by one actor. Lets discuss this with an example.


  


Single Responsibility Principle Limitations SRP creates too many classes doing one little thing, So try to find a balance.

Open Closed Principle

The open–closed principle states "software entities (classes, modules, functions, etc.) should be open for extension, but closed for modification". Functionality should be implemented by adding new classes, attributes and methods instead of changing the current ones or existing ones. Simplest way to apply OCP is to implement the functionality on new derived class or allow the client to access the original class with abstract interface.

Liskov Substation Principle

Liskov Substitution Principle (LSP) states that objects of a base class should be replaceable with objects of its derived class without breaking the application.

Interface Segregation Principle

Interface segregation principle (ISP) states that no code should be forced to depend on methods it does not use. or Whenever you have an interface you need everything that implements that interface to user every single potion of that interface. In the below example fly() cannot be implemented by a car so this is not valid as per principle.

interface vehicle{
   start()
   drive()
   fly()
}

class plane : vehicle{
   start(){
 
   }
   drive(){
 
   }
   fly(){
 
   }
}

class car : vehicle{
   start(){
 
   }
   drive(){
 
   }
   fly(){
      // error cannot fly 
   }
}

Dependency Inversion Principle

The dependency inversion principle is a specific methodology for loosely coupling software modules. Definition states that high level modules should not depend of low level modules, both should depend on abstraction and abstraction should not depend on implementation and implementation should depend on abstraction. Simply speaking high level modules or low level modules in your code should not depend on implementation and should depend on abstraction.

When following this principle, the conventional dependency relationships established from high-level, policy-setting modules to low-level, dependency modules are reversed, thus rendering high-level modules independent of the low-level module implementation details.

The principle states

  1. High-level modules should not import anything from low-level modules. Both should depend on abstractions (e.g., interfaces).
  2. Abstractions should not depend on details. Details (concrete implementations) should depend on abstractions.