This is an old revision of the document!
Encapsulate the Concept that Varies, i.e. a design is better when those parts that vary are encapsulated in a separate module.
This principle has two aspects that roughly correspond to the two sub-principles SRP and OCP. The first one is about making changes local. Everything which is supposed to change in the future should be encapsulated in a single module. This means cross-cutting concerns are avoided as much as possible. This is not completely possible but in many cases it is.
The second aspect is about introducing abstractions. Sometime the varying concept is one which varies at runtime rather than by maintenance. So at runtime it is decided upon a certain variation or there can be even several variations at the same time. In this case there has to be an abstract base class or an interface which encapsulates the varying concept. Several concrete descendant classes then specify the concrete variation.
The difference between the two aspects is whether the varying concept is one that changes over time during maintenance or one that may change at runtime. Nevertheless the advice is the same: encapsulate the concept that varies.
There are two reasons for this principle. The first reason is locality. When a varying concept is properly encapsulated in a single module, only this module is affected in case of a change. This reduces maintenance effort and ripple effects.
The second reason comes to play when the varying concept is implemented as an abstract class or interface. In this case a variation can be introduced without changing existing and tested code. This reduces testing effort (as already tested code does not need to be retested as it is not changed) as well as ripple effects (as the enhancement is done simply by adding a class. Note that for this rationale to work, the Liskov Substitution Principle also has to be adhered to.
See section contrary principles.
The principle is stated, explained and used in the GoF book:
Erich Gamma, Richard Helm, Ralph Johnson, John Vlissides: Design Patterns: Elements of Reusable Object-Oriented Software (“GoF book”), p. 29
But the idea if ECV is actually much older. It was first presented in
David Parnas: On the Criteria To Be Used in Decomposing Systems into Modules]// ===== Evidence ===== /* Comment out what is not applicable and explain the rest: */ /* * [[wiki:Proposed */ * Accepted: This principle was popularly described in the GoF book and can thus be regarded accepted. * Examined: Many of the patterns in the GoF book are precisely about encapsulating varying concepts. See strategies section. ===== Relations to Other Principles ===== ==== Generalizations ==== ==== Specializations ==== * Single Responsibility Principle (SRP): A responsibility in the sense of SRP is defined as “a reason for change”. This is a concept that varies over time. SRP tells that each module should have exactly one responsibility, i.e. the concept/responsibility should be encapsulated in that module. * Open-Closed Principle (OCP): The OCP demands encapsulating abstract concepts in base classes (or interfaces) in order to be able to enhance the module by subclassing which is possible without changing the previously written code. In this case several variations of a concept may exist in the code at the same time. There is always the abstract base class plus one or usually more concrete subclasses. So the OCP is about encapsulating abstract concepts that vary “in space”. ==== Contrary Principles ==== * More Is More Complex (MIMC): ECV demands adding a new class for a new varying concept. * Model Principle (MP): ECV sometimes results in classes which do not correspond top a real-world concept in the sense of MP. A “concept that varies” can also be a technical concept. ==== Complementary Principles ==== * Low Coupling (LC): ECV results in the creation of a new module. When introducing such a new module, LC has to be adhered to. * Liskov Substitution Principle (LSP): ECV may result in the introduction of an abstract base class. Here it is important to get the abstraction right. Otherwise LSP may be violated. * Generalization Principle (GP): Encapsulating a varying concept typically results in a more generally applicable solution. This is especially true when an abstract concept is encapsulated by introducing an interface or an abstract class. * Dependency Inversion Principle (DIP): ECV may result in the introduction of an abstract base class. Here DIP demands that other classes should only depend on this new abstract base class and not on the concrete subclasses. * Information Hiding/Encapsulation (IH/E): ECV tells that varying concepts should be encapsulated. IH/E then tells how encapsulation is done. ==== Principle Collections ====
===== Examples ===== ===== Description Status ===== Incomplete ===== Further Reading ===== * Erich Gamma, Richard Helm, Ralph Johnson and John Vlissides: Design Patterns: Elements of Reusable Object-Oriented Software * Single Responsibility Principle * Open-Closed Principle