Skip to main content
gamedev.net
🔒 Locked

std::vector problem after clearing

Started by Goishin 2 replies 800+ views
Original Post
Goishin
Goishin
I'm trying to implement a blockmap to do collision detection for particles using stl vectors. I've set up an array of std::vectors and then add the pointers to the particles that appear in that array location to the vector there. After I build the map, then I'll go through and compute any collisions. But after it goes through once, then it crashes. I've narrowed it down to the way I'm clearing out the vectors after each pass. But I don't know how to handle the vectors correctly. I want to be able to clear out the vectors in each array location, but I'm doing it wrong. Edit: I should add that the crash happens in the fill blockmap section after I move to a new location. If I keep adding particles to the original location, it works just fine. It's only when I add particles to a new location that every goes to hell Here's the code I've written:

//make the blockmap
std::vector<Particle*> blockmap[BLOCK_MAP_SIDE_SIZE * BLOCK_MAP_SIDE_SIZE];

//fill blockmap
if(sparks.size() > 1)
{
	for(std::vector<Particle>::iterator iter = sparks.begin(); iter != sparks.end(); iter++)
	{
		blockmap[iter->Get_BlockPos()].push_back(iter->Get_Pointer());
	}
}

//compute collisions
for(int i = 0; i < BLOCK_MAP_SIDE_SIZE * BLOCK_MAP_SIDE_SIZE; i++)
{
	if (blockmap.size() > 1)
	{
		for(std::vector<Particle*>::iterator iter = blockmap.begin(); iter != blockmap.end(); iter++)
		{
			//do collisiony stuff here
		}
	}
	blockmap.clear();
}


Any ideas what I'm doing wrong?
Zipster
Zipster
For starters, why are you mixing vectors and arrays? Just use one or another:

std::vector<std::vector<Particle*> > blockmap(BLOCK_MAP_SIDE_SIZE * BLOCK_MAP_SIDE_SIZE);

My guess is that you're trashing memory somewhere, but without seeing any more code or knowing exactly which line causes the crash (or what the crash even says), it's hard to tell. Start with the above change, and see if perhaps you're going out-of-bounds somewhere.
Goishin
Goishin
Ah, thanks Zipster. That wasn't it, but the line that I might be trashing my memory got me searching in the right direction. It ended up that I was computing my position into the blockmap wrong. I'm using an 8*8 blockmap, and I was ending up with values in the 300's. Once I fixed that, all my problems went away.

Thanks Zipster,

- Goishin
Zahlman
Zahlman
If your "collisiony stuff" doesn't explicitly require building lists of particles in the same cell (is it to do more detailed collision checks? If so, have you accounted for the possibility that two particles collide near a cell border?), you can do it a lot more simply. Even then, maybe this gives you some ideas for code cleanup:

Particle dummy;Particle* blockmap[BLOCK_MAP_SIDE_SIZE * BLOCK_MAP_SIDE_SIZE];// The if-check here was near useless; you're optimizing the unusual case.// Consider also that it's perfectly OK to iterate over an empty container.for (std::vector<Particle>::iterator iter = sparks.begin(); iter != sparks.end(); ++iter) {	Particle*& current = blockmap[iter->Get_BlockPos()];	if (!current) { current = &*iter; }	// you don't need a member function to get a pointer	else {		iter->collided();		if (current != &dummy) { current->collided(); current = &dummy; }	}}// BTW, standard library containers don't need to be explicitly .clear()ed at// the end; this happens automatically in their destructors.

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.