重新分配后的地址变更

时间:2014-09-01 10:14:24

标签: c++ c++11 stdvector reference-wrapper

在下面的代码中,每当有新成员插入std::vector<int>A时,由于内存重新分配,std::vector<reference_wrapper<int>>B指向错误的地址。是否可以使引用向量跟踪重新分配并始终存储正确的地址?

#include <iostream>
#include <functional>
#include <vector>
using namespace std;

int main()
{
    vector<int> A (0,3);
    vector<reference_wrapper<int>> B;
    B.push_back ( ref(A[0]) );
    B.push_back ( ref(A[1]) );
    B.push_back ( ref(A[2]) );

    A.push_back (0);

    cout << &A[0] << endl;
    cout << &B[0].get() << endl;

    return 0;
}

2 个答案:

答案 0 :(得分:1)

我看到的唯一方法是为向量保留足够的内存,以便在推回新元素时不会重新分配它,前提是不要在向量中间删除或插入元素。

考虑到这个陈述

vector<int> A (0,3);

错了。

必须有

vector<int> A (3,0);

或只是

vector<int> A (3);

你可以写

#include <iostream>
#include <functional>
#include <vector>
using namespace std;

int main()
{
    vector<int> A( 3 );
    A.reserve( 4 );

    vector<reference_wrapper<int>> B;

    B.push_back ( ref(A[0]) );
    B.push_back ( ref(A[1]) );
    B.push_back ( ref(A[2]) );

    A.push_back (0);

    cout << &A[0] << endl;
    cout << &B[0].get() << endl;

    return 0;
}

输出看起来像

0x9cbd018
0x9cbd018

答案 1 :(得分:0)

您没有指定此模式的实际使用情况。所以这里有一些可能的解决方案:

  1. 存储索引而不是引用/迭代器。
  2. 将A更改为列表或双端队列,它不会使实际更改的迭代器失效。
  3. 动态分配所有整数(例如std::shared_ptr<int>),让A和B都存储(共享)指针。