Issues with iterating through a vector of objects

I'm playing around with creating a very simple particle generator. Yet I find that when I store these particles in a vector I'm having issues accessing them and iterating through them.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

//If Vector has < 100 elements push back new particle with a random velocity.
if(pVect.size() < 100)
{
    Particle p(partRadius, winWidth/2, (winHeight - partRadius));
    p.setVelocity(rX, rY);
    pVect.push_back(p);
}

//Cycle through all elements in pVect and update the position and display the particle.

for(std::vector<Particle>::iterator i; i != pVect.end(); ++i)
{
    pVect[i].update();
    window.draw(pVect[i].getShape());
}


But when I try to cycle through the elements I get an error on what is line 14 here.;

no match for 'operator[]' (operand types are 'std::vector<Particle>' and 'std::vector<Particle>::iterator {aka __gnu_cxx::__normal_iterator<Particle*, std::vector<Particle> >}')

I'm not seeing what I'm doing wrong here.

BTW <vector> is included.
Last edited on
I can get it to work this way...

1
2
3
4
5
6
7
8
 for (auto& i : pVect)
{
    int tAlpha = i.getAlpha();
    i.setAlpha(tAlpha - 5);
    i.update();
    window.draw(i.getShape());

}


But then how do I erase an element if I need to?

Say I wanted to delete elements based off of their alpha value...

1
2
3
4
5
6
7
8
9
10
11
12
for (auto& i : pVect)
{
    int tAlpha = i.getAlpha();
    i.setAlpha(tAlpha - 5);
    i.update();
    window.draw(i.getShape());
    if (i.getAlpha() == 0)
    {
        pVect.erase(pVect.begin() + i);  // obviously not correct because i is not an iterator.
    }
}

Last edited on
1
2
i->update;
window.draw(i->getShape());

Or you can also use ranged for:
1
2
3
4
for (auto &particle : pVect){
    particle.update();
    window.draw(particle.getShape());
}
Well since i is not an integral type you can't use it as an index. Don't forget that an iterator is basically a pointer. Have you just tried to update and draw using the iterator?

1
2
i->update();
window.draw(i->getShape());


Hi, thanks for the replies.

Yes, I can get it to work fine using the ranged for, but I can't for the life of me think of how I'd delete an element if I do it that way. What I don't understand is why I can't iterate using []. i is a std::vector<Particle>::iterator. The error says that's what [] requires.

no match for 'operator[]' (operand types are 'std::vector<Particle>' and 'std::vector<Particle>::iterator {aka __gnu_cxx::__normal_iterator<Particle*, std::vector<Particle> >}')
Last edited on
Ok, maybe I'm losing my mind. This bit of code throws the same error.
1
2
3
4
5
6
7
8
9
10
11

    std::vector<int> nums;
    nums.push_back(22);
    nums.push_back(33);
    nums.push_back(55);

    for(std::vector<int>::iterator iter = nums.begin(); iter != nums.end(); ++iter)
    {
        std::cout << nums[iter] << std::endl;        
    }


I also get an error if I use nums.at(iter) instead of nums[iter]
In order to use an index the index must be an integral type, iter is an iterator which is not an integral type.

Perhaps something like the following:

1
2
for(i = 0; i < nums.size(); ++i)
    std::cout << nums[i] << std::endl;


Or perhaps:
1
2
3
4
    for(std::vector<int>::iterator iter = nums.begin(); iter != nums.end(); ++iter)
    {
        std::cout << *iter << std::endl;
    }


Ok, I thought that was the point of having iterators... to iterate through array type objects. I guess I need to read a bit more.
You can't pass an std::vector<T>::iterator to std::vector<T>::operator[](). An iterator is analogous to a pointer. You wouldn't expect this to work, would you?
1
2
3
int array[] = {1, 2, 3, 4];
int *i = array + 2;
array[i] = 42;

You have to dereference the iterator to access the element of the container, like I did in my previous post:
1
2
3
4
for(std::vector<Particle>::iterator i; i != pVect.end(); ++i){
    i->update;
    window.draw(i->getShape());
}

Also, generally you should not remove or add elements to a container while you're iterating it. std::vector in particular invalidates iterators on std::vector::erase(). If the vector reallocates while you're iterating it your program will crash if you're lucky, and it will do weird things if you're unlucky.
Topic archived. No new replies allowed.