Particle in Cell: efficient data structure handling I am building a simulation where you have 'Agents' distributed over a rather large landscape. Because the number of Agents is small, compared to the size of the landscape, I use the PIC approach where the landscape is divided into rather large cells and every cell can contain multiple agents - in contrast to a classical grid based approach. This should speed up spatial analysis.

I am asking whether there is a way to improve the code I came up with:

Agents contain an iterator to the node in the cell and a ptr to the cell containing the node

class Agent;

typedef std::list &lt;Agent*&gt; CELL;

class Agent {
  public:
  //...stuff...
    CELL::iterator cell_iter;
    CELL*cell_ptr;
};

class Grid {
  public:
    Grid(int dimx,int dimy,int cellsize);
    CELL *GetCell(double x,double y); 
 private:
    std::vector &lt;std::vector&lt;CELL&gt;&gt; grid_;
    int dimx_,dimy_,cellsize_,ncellx_,ncelly_;  
};


To add a new individual:

std::list &lt;Agent&gt; population;
//..stuff...
Agent seed(pos_x,pos_y,seed_type,10.1); // create a local agent
population.push_back(std::move(seed));
Agent *agent=&amp;population.back()
CELL *cell=GetCell(agent-&gt;x_,agent-&gt;y_); // get the cell for the agents pos
cell-&gt;push_back(agent); // add the agents ptr to the cell
agent-&gt;cell_ptr=cell; // save the agents cell to the agent
agent-&gt;cell_iter=--cell-&gt;end(); // save an iterator to the actual node


To delete an individual

auto iter=population.begin();
//...stuff...
(*iter).cell_ptr-&gt;erase((*iter).cell_iter); // erase the ptr to the agent from the cell
iter=population.erase(iter);
If you have move push_back then you should also have emplace_back. 

population.emplace_back(pos_x,pos_y,seed_type,10.1);


Erasing the individual means moving everyone that comes after. If you don't care about order then do a swap with back:

auto iter=population.begin();
//...stuff...
(*iter).cell_ptr-&gt;erase((*iter).cell_iter); // erase the ptr to the agent from the cell
std::swap(*iter, population.back());
population.pop_back();
//doesn't invalidate iter