What is the difference between Strategy design pattern and State design pattern?
Asked Answered
F

21

277

What are the differences between the Strategy design pattern and the State design pattern? I was going through quite a few articles on the web but could not make out the difference clearly.

Can someone please explain the difference in layman's terms?

Feverish answered 1/11, 2009 at 20:11 Comment(1)
Based on the answers here and my own observations, it seems that the implementations are largely (though not entirely) the same. Rather, the difference is mainly one of intent: we are trying to adapt behavior, either based on our state (state pattern), or based on something else (strategy pattern). Quite often that something else is "what the client chooses", through injection.Cephalochordate
B
166

Honestly, the two patterns are pretty similar in practice, and the defining difference between them tends to vary depending on who you ask. Some popular choices are:

  • States store a reference to the context object that contains them. Strategies do not.
  • States are allowed to replace themselves (IE: to change the state of the context object to something else), while Strategies are not.
  • Strategies are passed to the context object as parameters, while States are created by the context object itself.
  • Strategies only handle a single, specific task, while States provide the underlying implementation for everything (or most everything) the context object does.

A "classic" implementation would match either State or Strategy for every item on the list, but you do run across hybrids that have mixes of both. Whether a particular one is more State-y or Strategy-y is ultimately a subjective question.

Bernardinebernardo answered 12/10, 2012 at 23:10 Comment(1)
If you're counting the GoF as one of the popular choices, they would disagree that States are necessarily created by the context (can be created by the client and passed into the context, just like with Strategy).Inweave
C
139
  • The Strategy pattern is really about having a different implementation that accomplishes (basically) the same thing, so that one implementation can replace the other as the strategy requires. For example, you might have different sorting algorithms in a strategy pattern. The callers to the object does not change based on which strategy is being employed, but regardless of strategy the goal is the same (sort the collection).
  • The State pattern is about doing different things based on the state, while leaving the caller relieved from the burden of accommodating every possible state. So for example you might have a getStatus() method that will return different statuses based on the state of the object, but the caller of the method doesn't have to be coded differently to account for each potential state.
Clos answered 1/11, 2009 at 20:32 Comment(9)
but who changes the strategy in the strategy pattern ??Phthalocyanine
@Noor, usually it is a parameter or field of some kind. The actual caller's code isn't changed based on a change in strategy.Clos
yes this i understand, but can the caller itself change the strategy based on a decision?Phthalocyanine
@Noor, yes, but in any strategy pattern I can think of right now, it will be an up front decision that won't change in the middle.Clos
I'm with the same problem, State or Strategy, I think the diference in few words is, state, behavior is autodeterminated, strategy, behavior is determinated by caller.Alan
In eCommerce application, if extra discount needs to be applied on festive season, then it is state design pattern. The actual discount rate logic can be applied with strategy design pattern, if there are more than one way to arrive at that number.Skaggs
@Clos - This is a good answer. But it would be even better if combined with an example like this https://mcmap.net/q/108072/-what-is-the-difference-between-strategy-design-pattern-and-state-design-pattern. Some of the people reading this page might new programmers, coming from books "head first design patterns". So, examples would be nice to have.Wax
What if I want the caller agnostic to the state but still need the same goal with just different implementations? Would I use state or strategy? So I think the 2 points (A.Having different implementations for the same goal vs doing different things & B.Leaving the caller agnostic to the state on State pattern which stores a reference to the context vs having the caller aware of the injected Strategy) are related - usually when I want a completely different behavior and not just different implementations, SRP would advocate to encapsulate it in a State rather than having the caller aware of it.Aurelia
I like to think of which code smell each one avoids. Strategy would avoid if-else clauses within a single method, whereas State would avoid if-else clauses throughout potentially many different methods. So State needs more knowledge/higher coupling with the class, whereas Strategy is just the Client defining which tool the class will use.Shoreline
R
105

The difference simply lies in that they solve different problems:

  • The State pattern deals with what (state or type) an object is (in) -- it encapsulates state-dependent behavior, whereas
  • the Strategy pattern deals with how an object performs a certain task -- it encapsulates an algorithm.

The constructs for achieving these different goals are however very similar; both patterns are examples of composition with delegation.


Some observations on their advantages:

By using the State pattern the state-holding (context) class is relieved from knowledge of what state or type it is and what states or types that are available. This means that the class adheres to the open-closed design principle (OCP): the class is closed for changes in what states/types there are, but the states/types are open to extensions.

By using the Strategy pattern the algorithm-using (context) class is relieved from knowledge of how to perform a certain task (-- the "algorithm"). This case also creates an adherence to the OCP; the class is closed for changes regarding how to perform this task, but the design is very open to additions of other algorithms for solving this task.
This likely also improves the context class' adherence to the single responsibility principle (SRP). Further the algorithm becomes easily available for reuse by other classes.

Ribble answered 16/7, 2012 at 12:44 Comment(0)
B
62

Can somebody please explain in layman's terms?

Design patterns are not really "layman" concepts, but I'll try to make it as clear as possible. Any design pattern can be considered in three dimensions:

  1. The problem the pattern solves;
  2. The static structure of the pattern (class diagram);
  3. The dynamics of the pattern (sequence diagrams).

Let's compare State and Strategy.

Problem the pattern solves

State is used in one of two cases [GoF book p. 306]:

  • An object's behavior depends on its state, and it must change its behavior at run-time depending on that state.
  • Operations have large, multipart conditional statements that depend on the object's state. This state is usually represented by one or more enumerated constants. Often, several operations will contain this same conditional structure. The State pattern puts each branch of the conditional in a separate class. This lets you treat the object's state as an object in its own right that can vary independently from other objects.

If you want to make sure you indeed have the problem the State pattern solves, you should be able to model the states of the object using a finite state machine. You can find an applied example here.

Each state transition is a method in the State interface. This implies that for a design, you have to be pretty certain about state transitions before you apply this pattern. Otherwise, if you add or remove transitions, it will require changing the interface and all the classes that implement it.

I personally haven't found this pattern that useful. You can always implement finite state machines using a lookup table (it's not an OO way, but it works pretty well).

Strategy is used for the following [GoF book p. 316]:

  • many related classes differ only in their behavior. Strategies provide a way to configure a class with one of many behaviors.
  • you need different variants of an algorithm. For example, you might define algorithms reflecting different space/time trade-offs. Strategies can be used when these variants are implemented as a class hierarchy of algorithms [HO87].
  • an algorithm uses data that clients shouldn't know about. Use the Strategy pattern to avoid exposing complex, algorithm-specific data structures.
  • a class defines many behaviors, and these appear as multiple conditional statements in its operations. Instead of many conditionals, move related conditional branches into their own Strategy class.

The last case of where to apply Strategy is related to a refactoring known as Replace conditional with polymorphism.

Summary: State and Strategy solve very different problems. If your problem can't be modeled with a finite state machine, then likely State pattern isn't appropriate. If your problem isn't about encapsulating variants of a complex algorithm, then Strategy doesn't apply.

Static structure of the pattern

State has the following UML class structure:

PlantUML class diagram of State Pattern

Strategy has the following UML class structure:

PlantUML class diagram of Strategy Pattern

Summary: in terms of the static structure, these two patterns are mostly identical. In fact, pattern-detecting tools such as this one consider that "the structure of the [...] patterns is identical, prohibiting their distinction by an automatic process (e.g., without referring to conceptual information)."

There can be a major difference, however, if ConcreteStates decide themselves the state transitions (see the "might determine" associations in the diagram above). This results in coupling between concrete states. For example (see the next section), state A determines the transition to state B. If the Context class decides the transition to the next concrete state, these dependencies go away.

Dynamics of the pattern

As mentioned in the Problem section above, State implies that behavior changes at run-time depending on some state of an object. Therefore, the notion of state transitioning applies, as discussed with the relation of the finite state machine. [GoF] mentions that transitions can either be defined in the ConcreteState subclasses, or in a centralized location (such as a table-based location).

Let's assume a simple finite state machine:

PlantUML state transition diagram with two states and one transition

Assuming the subclasses decide the state transition (by returning the next state object), the dynamic looks something like this:

PlantUML sequence diagram for state transitions

To show the dynamics of Strategy, it's useful to borrow a real example.

PlantUML sequence diagram for strategy transitions

Summary: Each pattern uses a polymorphic call to do something depending on the context. In the State pattern, the polymorphic call (transition) often causes a change in the next state. In the Strategy pattern, the polymorphic call does not typically change the context (e.g., paying by credit card once doesn't imply you'll pay by PayPal the next time). Again, the State pattern's dynamics are determined by its corresponding fininte state machine, which (to me) is essential to correct application of this pattern.

Burin answered 24/5, 2015 at 14:18 Comment(2)
This answer was very helpful for me to make me distinguish the difference. The state machine argument sounds to be pertinent IMHO. This actually sums up the above answers in a theoretical computer science way.Jamilajamill
There is a difference between a state machine and the state pattern. In the pattern, states must be polymorphic: each state presents the same API. In the machine, transitioning to a new state can result in a new set of operations. Thus the pattern focuses more on designing the behavior within states, while the machine focuses more on designing the transitions between states.Antipyretic
S
30

Consider an IVR (Interactive Voice Response) system handling customer calls. You may want to program it to handle customers on:

  • Work days
  • Holidays

To handle this situation you can use a State Pattern.

  • Holiday: IVR simply responds saying that 'Calls can be taken only on working days between 9am to 5pm'.
  • Work days: it responds by connecting the customer to a customer care executive.

This process of connecting a customer to a support executive can itself be implemented using a Strategy Pattern where the executives are picked based on either of:

  • Round Robin
  • Least Recently Used
  • Other priority based algorithms

The strategy pattern decides on 'how' to perform some action and state pattern decides on 'when' to perform them.

Stafford answered 17/4, 2013 at 11:6 Comment(2)
This is an excellent answer and underrated. But, it would be helpful to mention why there is a need for many algorithms in your example. For example, the algorithm is chosen based on the preference of the Call center company. It would also help if there were simpler or trivial algorithms in your list for those who don't know RR or LRU. For example - Long time customer gets higher priority, Customer who waited most gets higher priority. Thanks !Wax
Wow! I really recommend this answer. A present Mode you are in .... VS .... the plan of action via an algorithm !Culp
S
27

The Strategy Pattern involves moving the implementation of an algorithm from a hosting class and putting it in a separate class. This means that host class does not need to provide the implementation of each algorithm itself, which is likely to lead to unclean code.

Sorting algorithms are usually used as an example as they all do the same kind of thing (sort). If each differing sorting algorithm is put into its own class, then the client can easily choose which algorithm to use and the pattern provides an easy way to access it.

The State Pattern involves changing the behaviour of an object when the state of the object changes. This means that the host class does not have provide the implementation of behaviour for all the different states that it can be in. The host class usually encapsulates a class which provides the functionality that is required in a given state, and switches to a different class when the state changes.

Statesmanship answered 1/11, 2009 at 21:20 Comment(0)
H
16

Strategy represents objects that "do" something, with the same begin and end results, but internally using different methodologies. In that sense they are analogous to representing the implementation of a verb. The State pattern OTOH uses objects that "are" something - the state of an operation. While they can represent operations on that data as well, they are more analogous to representation of a noun than of a verb, and are tailored towards state machines.

Housemaid answered 1/11, 2009 at 20:18 Comment(0)
N
12

Strategy: the strategy is fixed and usually consists of several steps. (Sorting constitutes only one step and thus is a very bad example as it is too primitive in order to understand the purpose of this pattern). Your "main" routine in the strategy is calling a few abstract methods. E.g. "Enter Room Strategy", "main-method" is goThroughDoor(), which looks like: approachDoor(), if (locked()) openLock(); openDoor(); enterRoom(); turn(); closeDoor(); if (wasLocked()) lockDoor();

Now subclasses of this general "algorithm" for moving from one room to another room through a possible locked door can implement the steps of the algorithm.

In other words subclassing the strategy does not change the basic algorithms, only individual steps.

THAT ABOVE is a Template Method Pattern. Now put steps belonging together (unlocking/locking and opening/closing) into their own implementing objects and delegate to them. E.g. a lock with a key and a lock with a code card are two kinds of locks. Delegate from the strategy to the "Step" objects. Now you have a Strategy pattern.

A State Pattern is something completely different.

You have a wrapping object and the wrapped object. The wrapped one is the "state". The state object is only accessed through its wrapper. Now you can change the wrapped object at any time, thus the wrapper seems to change its state, or even its "class" or type.

E.g. you have a log on service. It accepts a username and a password. It only has one method: logon(String userName, String passwdHash). Instead of deciding for itself whether a log on is accepted or not, it delegates the decision to a state object. That state object usually just checks if the user/pass combination is valid and performs a log on. But now you can exchange the "Checker" by one that only lets priviledged users log on (during maintanace time e.g.) or by one that lets no one log on. That means the "checker" expresses the "log on status" of the system.

The most important difference is: when you have choosen a strategy you stick with it until you are done with it. That means you call its "main method" and as long as that one is running you never change the strategy. OTOH in a state pattern situation during the runtime of your system you change state arbitrarily as you see fit.

Number answered 1/6, 2011 at 12:28 Comment(0)
H
11

In layman's language,

in Strategy pattern, there are no states or all of them have same state. All one have is different ways of performing a task, like different doctors treat same disease of same patient with same state in different ways.

In state Pattern, subjectively there are states, like patient's current state(say high temperature or low temp), based on which next course of action(medicine prescription) will be decided.And one state can lead to other state, so there is state to state dependency( composition technically).

If we technically try to understand it , based on code comparison of both, we might lose the subjectivity of situation,because both look very similar.

Hypesthesia answered 9/10, 2015 at 18:7 Comment(1)
Upvoted! It is very nice explanation! Thanks! :)Worshipful
T
5

Both Strategy and State pattern has the same structure. If you look at the UML class diagram for both patterns they look exactly same, but their intent is totally different. State design pattern is used to define and manage state of an object, while Strategy pattern is used to define a set of interchangeable algorithm and lets client to choose one of them. So Strategy pattern is a client driven pattern while Object can manage there state itself.

Tocci answered 27/8, 2013 at 11:2 Comment(0)
C
4

State comes with a little bit dependencies within the state derived classes: like one state knows about other states coming after it. For example, Summer comes after winter for any season state, or Delivery state after the Deposit state for shopping.

On the other hand, Strategy has no dependencies like these. Here, any kind of state can be initialized based on the program/product type.

Churchwarden answered 19/11, 2016 at 7:5 Comment(0)
M
3

Both patterns delegate to a base class that has several derivative, but it's only in the State pattern that these derivative classes hold a reference back to context class.

Another way to look at it is that the Strategy pattern is a simpler version of the State pattern; a sub-pattern, if you like. It really depends if you want the derived states to hold references back to the context or not (i.e: do you want them to call methods on the context).

For more info: Robert C Martin (& Micah Martin) answer this in their book, "Agile Principles, Patterns and Practices in C#". (http://www.amazon.com/Agile-Principles-Patterns-Practices-C/dp/0131857258)

Miniaturize answered 1/11, 2009 at 20:41 Comment(0)
S
3

This is a pretty old question, but still, I was also looking for the same answers and this is what I have discovered.

For State pattern lets consider an example of Medial Player Play button. When we do play it starts playing and makes the context aware that it is playing. Every time the client wants to perform play operation he checks the current state of the player. Now the client knows the state of the object is playing via the context object so he calls the pause state objects actions method. The part of the client realizing the state and on what state it needs to do action can be automated.

https://www.youtube.com/watch?v=e45RMc76884 https://www.tutorialspoint.com/design_pattern/state_pattern.htm

In the case of Strategy pattern, the arrangement of the class diagram is same as state pattern. The client comes to this arrangement to do some operation. That is instead of the different states there are different algorithms say for example different analysis that needs to be performed on the pattern. Here the clients tell the context what it wants to do that what algorithm (business defined custom algorithm) and then performs that.

https://www.tutorialspoint.com/design_pattern/strategy_pattern.htm

Both implements open close principle so the developer has the capability to add new states to the state pattern and new algorithm.

But the difference is what they are used that is state pattern used to execute different logic based on a state of the object. And in a case of strategy different logic.

Scythe answered 14/10, 2016 at 9:17 Comment(0)
B
3

In short, with the strategy pattern we can set some behavior on the fly, with state pattern, we can be sure, that an object will change its behavior internally with the change of its state.

Billie answered 28/4, 2018 at 18:14 Comment(0)
W
3

In my view, the main difference lies in their intentions. Technically, State and Strategy pattern look very similar. The main difference lies in:

  • The State pattern changes state of the context when it is required and state can be changed many times. So context changes its state or state can set another state
  • Strategy pattern sets strategy and strategy can be changed very rarely and context does not change its strategy.

Strategy pattern.

Our abstraction of some Sound strategies:

public interface ISound
{
    void Make();
}   
    

And its concrete strategies:

public class DogSoundStrategy : ISound
{
    public void Make()
    {
        Console.WriteLine("Bar");
    }
}

public class CatSoundStrategy : ISound
{
    public void Make()
    {
        Console.WriteLine("Meow");
    }
}

This is an abstraction of Animal who can make sound:

public abstract class Animal
{
    public void MakeSound(ISound sound)
    {
        sound.Make();
    }
}

And concrete animals look like this:

public class Dog : Animal
{
}

public class Cat : Animal
{   
}

And then we can call the above code like this:

Dog dog = new Dog();
dog.MakeSound(new DogSoundStrategy()); // there is a small chance 
    // that you want to change your strategy

Cat cat = new Cat();
cat.MakeSound(new CatSoundStrategy()); // there is a small chance 
    // that you want to change your strategy

There is a small chance that you want to change your strategy.

State pattern

Imagine you have a computer game where hero can be any super person in the world. Let's call him as Hero. He can run, swim and fly and change its shape to IronMan or SpiderMan. You have a button where you can change its shape or state to IronMan or SpiderMan.

The code of Hero would look like this:

public class Hero
{
    IState _state;

    public Hero()
    {
        _state = new SpiderManState();
    }

    public void Run()
    {
        _state.Run();
    }

    public void Swim()
    {
        _state.Swim();
    }

    public void Fly()
    {
        _state.Fly();
    }

    public void ChangeShape()
    {
        _state = _state.SetShape();
    }
}

Interface of IState would look like this:

public interface IState
{
    void Run();

    void Swim();

    void Fly();

    IState SetShape();
}

And concrete states look like this:

public class SpiderManState : IState
{
    public void Fly()
    {
        Console.WriteLine("Spiderman is flying");
    }

    public void Run()
    {
        Console.WriteLine("Spiderman is running");
    }

    public void Swim()
    {
        Console.WriteLine("Spiderman is swimming");
    }

    public IState SetShape()
    {
        return new IronManState();
    }
}

and IronManState would look like this:

public class IronManState : IState
{
    public void Fly()
    {
        Console.WriteLine("IronMan is flying");
    }

    public void Run()
    {
        Console.WriteLine("IronMan is running");
    }

    public void Swim()
    {
        Console.WriteLine("IronMan is swimming");
    }

    public IState SetShape()
    {
        return new SpiderManState();
    }
}

And now by clicking button ChangeShape() of Hero class, you will be able to change State of hero from, e.g. SpiderMan to IronMan.

So State of Context (Hero) depends on and can be changed by its button ChangeShape. And it can occur many times.

There is a high chance that you want to change context's state.

State pattern is also can be considered as an alternative to replace many if — else statements in class.

Worshipful answered 25/10, 2020 at 19:47 Comment(0)
R
2

The difference is discussed in http://c2.com/cgi/wiki?StrategyPattern. I have used the Strategy pattern for allowing different algorithms to be chosen within an overall framework for analysing data. Through that you can add algorithms without having to change the overall frameworks and its logic.

A typical example is that you amy have a framework for optimising a function. The framework sets up the data and parameters. The strategy pattern allows you to select algorithms such as sttepest descents, conjugate gradients, BFGS, etc. without altering the framework.

Reeher answered 1/11, 2009 at 20:18 Comment(0)
H
2

Both of the patterns are used for changing the behavior of an object,

By design, the state pattern object has a single state and the behavior of an object is based on the implemented single state (Class) and its subclasses.

In contrast, the strategy doesn't have a single state, and the behavior of an object is determined by the implementation of the different strategy objects.

Hypertensive answered 6/12, 2020 at 3:57 Comment(0)
A
1

When you have a project which can be divided into 2 tasks:

task 1: you can use one of two different algorithms to accomplish: alg1, alg2

task 2: you can use one of three different algorithms to accomplish: alg3, alg4, alg5

alg1 and alg2 are interchangeable; alg3, alg4 and alg5 are interchangeable.

Choosing which algorithm to perform in task 1 and task 2 depends on states:

state 1: you need alg1 in task 1 and alg3 in task 2

state 2: you need alg2 in task 1 and alg5 in task 2

You context can change state object from state 1 to state 2. Then your task would be accomplished by alg2 and alg5, instead of alg1 and alg3.

You can add more interchangeable algorithms for task 1 or task 2. This is strategy pattern.

You can have more states with different combination of algorithms in task 1 and task 2. State pattern allows you to switch from one state to another and perform different combination of algorithms.

Alis answered 14/3, 2019 at 22:30 Comment(0)
T
1

'Strategy' is only an algorithm that you can change it in different circumstances upon your need, and it processes something for you. Ex. you can choose how compress a file. zip or rar ... in a method.

But 'State' CAN change all your object behaviour, when it changes, Even it can change other fields... that's why it has a reference to its owner. You should notice that changing an object field can change object behaviour at all. Ex. when you change State0 to State1 in obj, you change an integer to 10.. so when we call obj.f0() that do some calculation and use that integer, it affects the result.

Tarttan answered 12/9, 2019 at 7:2 Comment(0)
P
0
  1. In Strategy pattern while implementing searching , we can have multiple strategies of searching e.g NaiveStrategy(), KMPStrategy() or RabinKarp() Strategy. These are all independent and there are somewhat stable choices. And most important, strategies can't shift from one another. Only Context is able to change strategies.
  2. State Pattern on the other hand is based on concept of Finite-State Machines. The states can transition from one another. Here states are less stable as compared to the strategies. And one thing, each concrete state maintains a reference to context and hence is able to transition to another state.

So crux is that, in strategy only context can set the strategy while in case of state pattern states can perform transition to other states. Strategies are unaware of each other in Strategy Pattern. While States are not unaware of each other in State Pattern and allow transition as they maintain a reference to context object.

"Strategy makes these objects completely independent and unaware of each other. However, State doesn’t restrict dependencies between concrete states, letting them alter the state of the context at will."

Reference : https://refactoring.guru/design-patterns/strategy

Presignify answered 10/1, 2022 at 23:56 Comment(0)
B
0

The state pattern is used to represent objects that can change their behavior depending on their state. The context class in the state pattern can only have a reference to one state interface. This is because the state of an object can only be one thing at a time.

The strategy pattern is used to represent objects that can use different algorithms to perform a task. The context class in the strategy pattern can have a reference to more than one strategy interface. This is because the context object can use different algorithms depending on the situation.

This is the main difference between the state and strategy patterns.

Burning answered 16/6, 2023 at 8:5 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.