A cornerstone of clear code is the division of its various behaviors into small, manageable pieces.
Clear code requires you to keep less knowledge in your head at any given time, making the code simpler to
reason about. Short segments of code with clear intent are a big step in this direction, but bits of code
should not be broken up along arbitrary boundaries. Separating them by concern is an effective approach.
A concern is a distinct behavior or piece of knowledge your software deals with. Concerns can range
in granularity from how to calculate a square root to how payments are managed in an e-commerce system.
One way to distinguish separate concerns is to follow the Unix philosophy of “do one thing and do it well.”
When a particular function or class in your code is concerned with a single behavior, you can improve it independent of
the code that uses it. In contrast, if behaviors are duplicated and mixed together throughout your code, it may be difficult
to update a particular behavior without thinking about—and in the worst case, breaking—several other behaviors.
Many functions on a website, for example, might rely on information from the currently authenticated user.
If they all check authentication and fetch information about that user themselves, they’ll all need to be updated when
the details about authentication change. That’s a lot of work, and if one function is missed, it may start doing unexpected
things or stop working altogether.
Separation of Concern at the grass root level is the Single Responsibility principle in SOLID.
Applying the principle of separation of concerns to software design can result in a number of residual benefits. First, the lack of duplication and singularity of purpose of the individual components render the overall system easier to maintain. Second, the system as a whole becomes more stable as a byproduct of the increased maintainability. Third, the strategies required to ensure each component only concerns itself with a single set of cohesive responsibilities often result in natural extensibility points. Forth, the decoupling which results from requiring components to focus on a single purpose leads to components which are more easily reused in other systems, or different contexts within the same system. Fifth, the increase in maintainability and extensibility can have a major impact on the marketability and adoption rate of the system.
SOC is used in the Calculator Program such that the program is broken into distinct features that overlap
in functionality as little as possible. We have broken the original problem of creating a Calculator
to perform Addition into four independent tasks:
Calculation class with abstract method with encapsulation to define the input values
Addition class that adds two or more numbers
Function to add the Calculation to history
Calculator class that performs Addition as well as stores the value in the history
In all the above four, all the classes have been
separated by function, the get_result is first defined in a different class Calculation and then gives us the result of the addition, the add_calculation adds the calculation to history
and the add_numbers function calls the other two functions together to finally create the proper calculator
functionality. The four separate classes come together to form the Calculator program, but each action or concern
is being handled separately and independently
Here it is obvious that the functions have been separated by their concern i.e. their duty, and each of these functions can be reused
as well as easily modified to accommodate any other new changes or functionality
The Single Responsibility Principle is also something that on a class/object level is the same as Separation of Concern, however the SoC is not limited to Architecture Layers, it’s also applied on many other things, such as: an object that could represent a concern from language point view, SOA can separate concerns into services, separating behaviour as concern in logical units.