向量不是“保存值” C ++

时间:2018-10-24 14:00:08

标签: c++ vector

当从向量读取时,我将值设为零。我有:

class Graph {
public:
    vector<Vertex> vertices;
};

class Vertex {
public:
    vector<int> adjacentVertices;
};

然后在我的加载方法中:

int vertices, edges;
cin >> vertices >> edges;
Graph mainGraph;
mainGraph.vertices.reserve(static_cast<unsigned int>(vertices));
int tmp1, tmp2;
for (int i = 0; i < edges; i++) {
    cin >> tmp1 >> tmp2;
    mainGraph.vertices[tmp1].adjacentVertices.push_back(tmp2);
    cout << mainGraph.vertices[tmp1].adjacentVertices.size(); //PRINTS NUMBERS -> SEEMS OKAY
}

cout << mainGraph.vertices.size(); //IS ZERO???

for(const Vertex &v : mainGraph.vertices){ //CRASHES
    cout << v.adjacentVertices.size();
}

我敢打赌这很愚蠢,但是我想念什么呢?我读到,如果不需要特殊的构造函数,向量将在使用时自行自我构造。

3 个答案:

答案 0 :(得分:8)

更改此:

mainGraph.vertices.reserve(static_cast<unsigned int>(vertices));

对此:

mainGraph.vertices.resize(static_cast<unsigned int>(vertices));

由于使用https://jsfiddle.net/8kbcyfsn/,因此不会创建向量的单元格,尽管可以使用reserve()完成。

结果,在您执行mainGraph.vertices[tmp1]时,您会在代码中调用未定义行为(UB),因为您试图访问尚未构造的对象!

答案 1 :(得分:7)

reserve不会更改vector的大小或构造项目。它只会分配在添加元素时将保留的内存。

您对mainGraph.vertices[tmp1]的调用未定义,因为它正在访问原始内存。

使用reserve代替resize来分配和构造项目。

答案 2 :(得分:0)

发生这种情况是因为您试图手动管理向量的大小。让STL动态地完成所有工作:

Graph mainGraph;
int edge;

while (cin >> edge)
{
    Vertex newVertex;
    newVertex.adjacentVertices.push_back(edge);
    mainGraph.vertices.push_back(std::move(newVertex));
}

for(const Vertex &v : mainGraph.vertices)
    cout << v.adjacentVertices.size();

https://ideone.com/BQq01W