I am trying to understand the strategy pattern, here is an example, we have a Customer
that has a method GetDiscount
, this method is written as follows
GetDiscount
If (Condition1)
Return 10%
else (Condition2)
Return 20%
Now I have refactored the code using the strategy pattern so it becomes
GetDiscount
Invoke the attached strategy
And we create two strategy class 10%Strategy
and 20%Strategy
to encapsulate the behavior of the discount
And for the client code to use the customer class it becomes
c = new Customer
if(condition1)
c.attach(10%Strategy)
else (condition2)
c.attach(20%Strategy)
c.GetDiscount
So as you can see we have moved the conditionals from inside Customer
class into the client code, not only this, but this conditional branching itself is considered a business logic and we let it to leak into client code that might be a presentation controller for example.
Am I missing something?
In large software systems developed with object-oriented techniques you have code that assembles objects, and code that uses the assembled objects. In your case, the code that calls attach
is assembling Customer
object for later use, and the code that calls GetDiscount
is one that makes use of the object.
The goal the strategy pattern fulfills is moving the decision of which discount the Customer
gets form the point where the object is used to the point where the object is assembled. The condition remains in your code, but it is now confined to the place where you create your Customer
object.
Once the assembly is done, the Customer
object becomes self-sufficient. The data that you used to compute the condition for 10% or 20% discount is no longer required, because it is embedded in the type of discount. The logic for computing a discount follows the Customer
into different places in code. You can use discount computation without duplicating the logic in multiple places - for example, to compute the total price of sale, to preview the price of an individual item, to process a return, and so on. This also saves you from duplicating the same logic when the computation is needed more than once.