 # SOLID: Open Close Principle

### Open Close Principle

If you have not read Single Responsibility Principle Start from here Single Responsibility Principle

`Classes should be open for extension, but closed for modification`

This principle states that any new functionality can be added in a system with minimum modification in the current code. Means the system should be open to additions but it should also closed for modification (or less modification).

A class is closed when it is compiled or shared as library but it is also open since any new class can use it as parent and add new functionality.

The best way to implement Open Close Principle is to start with Single Responsibility Principle (So that each class have only one responsibility) and let the consumer class talk to different classes with abstraction (Interface, So that consumer class need not to know about concrete implementation).

Let’s assume we have an `AreaCalculator` class which calculates the sum of areas of different shape like this:

```class AreaCalculator {
public double area(Object[] shapes) {
double area = 0;
for (Object shape in shapes) {
if (shape instanceof Square) {
Square square = (Square)shape;
area += Math.sqrt(square.height);
}

if (shape instanceof Triangle) {
Triangle triangle = (Triangle)shape;
double totalHalf = (triangle.firstSide + triangle.secondSide + triangle.thirdSide) / 2;
area += Math.sqrt(totalHalf * (totalHalf - triangle.firstSide) *
(totalHalf - triangle.secondSide) * (totalHalf - triangle.thirdSide));
}

if (shape instanceof Circle) {
Circle circle = (Circle)shape;
}
}
return area;
}
}

class Square {
public double height;
}

class Circle {
}

class Triangle {
public double firstSide;
public double secondSide;
public double thirdSide;
}```

So in above example what if we have to add one more Shape? we have to change the `AreaCalculator` class. So this class doesn’t follow OCP (closed to modification).

Let’s see the following code:

```class AreaCalculator {
public double area(Shape[] shapes) {
double area = 0;
for (Shape shape in shapes) {
area += shape.area();
}
return area;
}
}

interface Shape {
public double area();
}

class Square implements Shape {
double height;

public double area() {
return Math.sqrt(height);
}
}

class Circle implements Shape {

public double area() {
}
}

class Triangle implements Shape {
double firstSide;
double secondSide;
double thirdSide;

public double area() {
double totalHalf = (firstSide + secondSide + thirdSide) / 2;
return Math.sqrt(totalHalf * (totalHalf - firstSide) *
(totalHalf - secondSide) * (totalHalf - thirdSide));
}
}```

Now, In this code if we have to add a new Shape we just need to create a class and implement the `Shape` interface. There is no modification needed in `AreaCalculator` class, so it is closed to modification as well as open to extension.

Next: Likov’s Substitution Principle