4

我正在使用如下代码:

const int MY_SIZE = 100000;
std::vector<double> v;
v.reserve(MY_SIZE);

// add no more than MY_SIZE elements to the vector

f(v);    
v.clear();

// again, add no more than MY_SIZE elements to the vector

f(v);
v.clear();

//
// etc...
//

我的代码的重点是存储MY_SIZE double's 然后f(std::vector<double>)对这些元素执行操作。在我填满向量并执行操作后,我想摆脱所有元素(并重置std::vector::size()为 0),然后添加更多元素。但是,这里的关键是我不想改变分配给向量的内存空间。

请注意,我永远不会向 中添加多个MY_SIZE元素v,因此v永远不需要重新分配比v.reserve(MY_SIZE).

那么,当我调用v.clear()上面的代码时,它会以任何方式影响分配的空间量v.reserve(MY_SIZE)或内存中的位置v.begin()吗?


相关问题:如果我打电话v.erase(v.begin(),v.begin()+v.size()),它会以任何方式影响分配的空间量v.reserve(MY_SIZE)或内存中的位置v.begin()吗?

如果我真的只是想擦除所有元素,我会调用clear(). 但是我想知道这个相关问题,因为有时我只需要擦除 的前 X 个元素v,并且在这些情况下,我想保留分配的内存v.reserve(MY_SIZE)并且我不希望v更改 的位置。

4

1 回答 1

1

似乎 C++ 标准 (2003) 隐含地保证如果clear()erase()调用std::vector.

根据序列(表 67)的要求,a.clear()等价于a.erase(begin(),end())

此外,标准规定 的erase(...)成员函数std::vector<T>不会抛出异常,除非 T 的复制构造函数抛出异常(第 23.2.4.3 节)。因此它是隐式保证的,因为重新分配可能会导致异常(第 3.7.3、20.4.1.1 节)。

v.begin()保持不变,因为erase(...)只会在擦除点之后使所有迭代器无效(第 23.2.4.3 节)。但是,它不会是可取消引用的(因为v.begin() == v.end())。

所以,如果你有一个符合标准的实现,你很好......

更正

我的推理是有缺陷的。我设法证明它erase(...)不会重新分配,但是如果您擦除所有元素,实现仍然可以释放内存。但是,如果a.capacity()在擦除/清除后报告“您可以在不重新分配内存的情况下添加 N 个元素”,那么您就可以了。

C++11 标准定义a.clear()不参考a.erase(...). a.clear()不允许抛出异常。因此它可以解除分配,但不能重新分配。所以你应该在清除向量后检查容量,以确保内存仍然存在并且下一次调整大小不会重新分配。

于 2013-07-23T17:27:05.383 回答