# How do I contiguously store and iterate over ECS components in C++?

I'm writing an entity component system and want to store each type of component separately and contiguously in memory in a way that's easy to iterate over.

Component is a simple base class from which like classes like MoveComponent derive.

I store components inside the World class:

struct World {
...
std::vector<Component> components;
};


This would work fine if there was only one type of component, just a Component class. The problem is I don't know how to handle component subclasses. For example every MoveComponent should be stored contiguously in memory in a way that I can easily iterate over and process them.

I want to avoid this kind of copy-paste junk code for hopefully obvious reasons:

struct World {
...
std::vector<MoveComponent> move_components;
std::vector<PhysicsComponent> physics_components;
etc.
};


I'd like to instead structure it in a way that permits iterating over each component of a certain type in a World like, for example, this (inspired by Overwatch's entity component system video, see here):

for (MoveComponent *mc : ComponentIterator<MoveComponent>(world)) { ... }


I'm at a loss as to how to implement this.

• Did you check how EnTT does it? – Vaillancourt Apr 3 at 3:18
• I recommend avoiding Blizzard's presentations, they often oversell their achievements while also being shallow on technical details. For example, you are not supposed to iterate over single component; rather, system is supposed to iterate over the set of multiple components. – Shadows In Rain Apr 3 at 4:53

Entity component systems store data in one of three ways:

1. Centrally allocated arrays, accessable by all systems.
2. Contigious arrays of subsets of components that each system is interested in.
3. Contigious array of "entities" allocated in a centrally located memory buffer.

Naughty Dog uses scenario 1. An entity in this context is just a collection of numbers:

struct Entity
{
static const int FOO = 0;
static const int BAR = 1;
int components[MAX_COMPONENTS];
uint32_t id;
};


The "components" in the above code are either "-1" meaning "no component of this type, or a positive number, zero inclusive. This is an index to a centrally stored array of each set of components:

class ComponentAllocator
{
public:
FooComponent foo_components[MAX_FOO_COUNT];
BarComponent bar_components[MAX_BAR_COUNT];
};


Then any system can use some singleton/service locator pattern to get access to it, and iterate over it:

void FooBarSystem::update()
{
for (auto& entity: entities) //entities is just a collection of type Entity
{
Foo& foo = getComponentAllocator().foo_components[entity.components[FOO]];
Bar& bar = getComponentAllocator().bar_components[entity.components[BAR]];
// Do something that requires interaction between foo and bar.
// ...
}
}


In scenario 2, your entity is the storage for each set of components, and each system stores a collection of proxies to that entity.

class Entity
{
public:
std::map<std::type_index, std::shared_ptr<IComponent>> m_Components;
uint32_t id;