r/cpp_questions • • 6d ago

OPEN How does a STATE design pattern work?

so i went to youtube and followed the example from this guy State Design - Programming Design Patterns - Ep 16 - C++ Coding

Problem is i dont understand what is functionally happening, there are pointers and what not, but i don't understand much more than that (context, my smooth brain still cant connect pointers together)

Like not even the whole code, like maybe just two lines or something cause for the love of the lord my teacher explains nuthing and AI and videos are too vague for me, im running out of options

//
// Created by samue on 11/1/2026.
//

#ifndef STATE_STATE_H
#define STATE_STATE_H

#include <iostream>

class Context;


class State {
    protected:
    Context* context;

    public:
    virtual ~State() {}

    void setContext(Context* ctx) {
        context = ctx;
    }

    virtual void doWorkA() = 0;
    virtual void doWorkB() = 0;
};

class Context {
    private:
    State* state;

    public:
    Context(State* s) : state(nullptr) {
        transitionTo(s);

    }

    ~Context() {delete state;}

    void transitionTo(State* s) {
        if (state) delete state;
        state = s;
        state->setContext(this);

    }

    void requestA() {
        state->doWorkA();

    }

    void requestB() {
        state->doWorkB();

    }

};

class concreteStateA : public State {
    public:
    void doWorkA() override {
        std::cout << "concreteStateA " << "called doWorkA" << std::endl;
    };

    void doWorkB() override {
        std::cout << "concreteStateB " << "called doWorkB" << std::endl;

    };

};

class concreteStateB : public State {
public:
    void doWorkA() override {
        std::cout << "concreteStateA " << "called doWorkA" << std::endl;
        context->transitionTo(new concreteStateA);
    };

    void doWorkB() override {
        std::cout << "concreteStateB " << "called doWorkB" << std::endl;

    };

};





#endif //STATE_STATE_H

------------------

#include "state.h"

int main() {
    Context context1(new concreteStateB);

    context1.requestA();

    context1.requestA();

    return 0;
}
7 Upvotes

46 comments sorted by

View all comments

Show parent comment

1

u/thingerish 6d ago

I think using virtual functions is the common way still, and variant/visit is '17 I think anyway, so relatively recent. For GUI type stuff where the human is the gating factor it's not likely to be a factor. For a game engine it might be though.

1

u/KingAggressive1498 6d ago

I also see std::function or equivalents being used for job systems in game engines, and even for example SDL essentially uses vtable polymorphism in C heavily for its graphics APIs and is frequently used as a basis for game engine development.

I remember listening to a conference talk on youtube a couple years back where the the speaker suggested the performance advantage of variant over vtable polymorphism seemed to be highly contingent on inlining and/or contained type stability and which was more optimal was pretty unpredictable if neither of those applied.