I have a problem in a piece of code I’m writing. I’ve boiled it down to this example which produces the same results (in principal).
Basically I’ve got a vector of pointers to Objects that I come across in one class, and pass to another. I then notice that by going through this vector with an iterator I come across NULL or garbage values, whereas using a traditional for-loop runthrough everything’s fine.
Here’s the code:
#include <iostream>
#include <vector>
using namespace std;
class MyObject
{
public:
int a;
int b;
MyObject(int _a, int _b)
{
a = _a; b = _b;
}
};
class Builder
{
public:
Builder() {
obj_vector.push_back(new MyObject(1, 2));
obj_vector.push_back(new MyObject(3, 4));
}
vector<MyObject*> getObjectVector() { return obj_vector; }
private:
vector<MyObject*> obj_vector;
};
class MyObjectHolder
{
public:
MyObjectHolder()
{
Builder builder;
obj_vector = builder.getObjectVector();
}
vector<MyObject*> getObjectVector() { return obj_vector; }
private:
vector<MyObject*> obj_vector;
};
int main()
{
MyObjectHolder holder;
for (vector<MyObject*>::iterator itr = holder.getObjectVector().begin(); itr != holder.getObjectVector().end(); ++itr)
{
if ((*itr) == NULL) {
cout << "NULL" << endl;
}
else
{
cout << (*itr)->a << "\t" << (*itr)->b << endl;
}
}
cout << endl;
for (unsigned int i = 0; i < holder.getObjectVector().size(); i++)
{
if (holder.getObjectVector()[i] == NULL)
cout << "NULL" << endl;
else
cout << holder.getObjectVector()[i]->a << "\t" << holder.getObjectVector()[i]->b << endl;
}
return 0;
}
And the output of this program is:
0 0
3 4
1 2
3 4
So I’m wondering why the iterator object produces garbage values. In other instances the iterator does equal NULL. I’m guessing it has something to do with some of the bbjects going out of scope while being passed around between objects, but I can’t figure out where or why.
Thanks
holder.getObjectVector()returns a newvector. Soholder.getObjectVector().begin()andholder.getObjectVector.end()are unrelated, as exists inforloop.Changing
getObjectVector()to return a reference would correct this:EDIT:
An alternative would be to arrange to call
getObjectVector()once before theforloop and store the result and it would not be necessary to return a reference: