Laurent
Laurent

Reputation: 842

keeping track of vector elements addresses

I want to know if there is a way to keep track of addresses of elements in a vector.

I like to use vector of solid elements like std::vector<MyObject> vec because:

This is exactly what I want. The problem arises when I want to store the address / reference of elements of my vector in other objects. In fact, the problem really arises when std::vector need to reallocate memory.

I tried to find alternatives to my problem:

What I would loved to have is a vector that can give me a pointer object that will allways point the the address of the desired element and I will use it like that :

std::vector<MyObject> vec;
// insert some elements
...
// get a pointer object by index or by using an iterator
// does something like that exist?
std::vector<MyObject>::pointer ptr = vec.get_pointer_at(5); 

// do what I want on the vector except removing the element
...

// use my pointer whatever reallocations occurred or not
ptr->doSomething();

That sounds like an iterator that will never be invalidated except the fact I don't need/want to perform arithmetic on it (+x, -x, ++, --).

So, can someone leads me to the way to achieve what I want or explain me why/where I'm wrong wanting to do this? Please accept my apologize for my lack of knowledge in STL if there is a well known solution that I missed / or if this question has already be answered.

Edit:

I think that if I have to code such kind of pointer, that means that I'm wanting something useless or I'm wrong somewhere (unless someone should have already wrote a template for that) . So I'm more looking to a validated C++ idiom to get rid of this problem.

Upvotes: 3

Views: 1656

Answers (2)

Julien
Julien

Reputation: 2248

As far as I know, there is nothing in the standard library nor in Boost to address your problem. A solution would be to implement your own kind of element pointer:

template<typename T>
class vector_element
{
public:
    vector_element( std::vector<T>& v, std::size_t i )
      : m_container( v ), m_element_index(i)
    { }

    T& operator*() { return m_container[m_element_index]; }
    T* operator->() { return &m_container[m_element_index]; }
private:
    std::vector<T>& m_container;

    std::size_t m_element_index;
};

Upvotes: 0

Sergey Kalinichenko
Sergey Kalinichenko

Reputation: 726579

Although std::vector does not give you such pointer, there is no reason why you cannot make one yourself. All it takes is a class that keeps a reference to the std::vector object and the index, and overloads the prefix operator * and the infix operator -> (you need four overloads - const and non-const for each operator).

You would use this pointer like this:

std::vector<int> vect = {2, 4, 6, 8, 10, 12, 14, 16};
vect_ptr<int> ptr(vect, 5); // <<== You need to implement this
*ptr = 123;
cout << *ptr << endl;

The implementation of these overloads would grab the std::vector's begin() iterator, and return the result of calling vect.at(index). This would look like a pointer from the outside, but the object to which it points would change as the content of the std::vector gets resized.

Upvotes: 2

Related Questions