container.clear() free/reallocate 内部缓冲区吗?
Does container.clear() free/reallocate internal buffers?
如果我有一个容器并在其上调用 clear()
,那么 只是 破坏里面的所有元素还是实际上 free/allocate 新内存内部也是?这种行为是否超出了 C++ 标准的范围?
归结为:
unordered_set<int> mySet { 1, 2, 3, 4, 5 };
mySet.reserve(1000);
mySet.clear();
//Is this pointless/redundant
//or should I treat my container like it was just constructed?
mySet.reserve(1000);
对 ideone (http://ideone.com/XQi8IT) 的快速测试表明,内部内存缓冲区在调用清除后保留。因此,至少对于 unordered_set
上的新版本 g++ 是这样。我的问题是 1) 标准说了什么,如果有的话,以及 2) 这种行为是否在所有容器中都是一致的。
未指定内存发生了什么。它只是定义了以下要求:
对于序列容器,我们对 clear()
有以下要求:
[C++11 §23.2.3]
Table 100
Destroys all elements in a
. Invalidates all references, pointers,
and iterators referring to the elements of a
and may invalidate the
past-the-end iterator.
post: a.empty()
returns true
其中并没有真正提到内存。对于关联容器,我们有 clear()
:
的要求
[C++11 §23.2.4]
Table 102
a.erase(a.begin(),a.end())
这导致 erase(...)
要求是:
erases the element pointed to by q
. Returns an iterator pointing to the element immediately following q
prior to the element being erased. If no such element exists, returns a.end()
同样,没有提及容器内存缓冲区的容量。然后我们有具有类似措辞的无序关联容器:
[C++11 §23.2.5]
Table 103
Erases all elements in the container. Post: a.empty()
returns true
总的来说,标准没有提到 clear
之后内部内存缓冲区发生的任何事情。所以这是未指定的行为,可能因不同的实现而异。
由于 reserve
并非在所有容器中都可用(这确实会改变容量),而且下一个最好的东西也不是 (shrink_to_fit
),因此似乎没有一个很好的方法来始终如一地清除容器的内部内存。
C++ 标准没有要求任何标准容器释放任何内存。甚至函数 std::vector<T>::shrink_to_fit()
也只是请求缩小内存。这个函数被认为可以取代像
这样的成语
std::vector<T>().swap( myVector );
这个成语是用来真正释放内存的,std::vector<T>::clear()
不保证。 (事实上,std::vector<T>::clear()
被指定为保持 capacity()
不变。)你仍然可以将这个惯用语用于其他没有函数 shrink_to_fit()
的容器。
如果我有一个容器并在其上调用 clear()
,那么 只是 破坏里面的所有元素还是实际上 free/allocate 新内存内部也是?这种行为是否超出了 C++ 标准的范围?
归结为:
unordered_set<int> mySet { 1, 2, 3, 4, 5 };
mySet.reserve(1000);
mySet.clear();
//Is this pointless/redundant
//or should I treat my container like it was just constructed?
mySet.reserve(1000);
对 ideone (http://ideone.com/XQi8IT) 的快速测试表明,内部内存缓冲区在调用清除后保留。因此,至少对于 unordered_set
上的新版本 g++ 是这样。我的问题是 1) 标准说了什么,如果有的话,以及 2) 这种行为是否在所有容器中都是一致的。
未指定内存发生了什么。它只是定义了以下要求:
对于序列容器,我们对 clear()
有以下要求:
[C++11 §23.2.3]
Table 100
Destroys all elements in
a
. Invalidates all references, pointers, and iterators referring to the elements ofa
and may invalidate the past-the-end iterator.post:
a.empty()
returnstrue
其中并没有真正提到内存。对于关联容器,我们有 clear()
:
[C++11 §23.2.4]
Table 102
a.erase(a.begin(),a.end())
这导致 erase(...)
要求是:
erases the element pointed to by
q
. Returns an iterator pointing to the element immediately followingq
prior to the element being erased. If no such element exists, returnsa.end()
同样,没有提及容器内存缓冲区的容量。然后我们有具有类似措辞的无序关联容器:
[C++11 §23.2.5]
Table 103
Erases all elements in the container. Post:
a.empty()
returnstrue
总的来说,标准没有提到 clear
之后内部内存缓冲区发生的任何事情。所以这是未指定的行为,可能因不同的实现而异。
由于 reserve
并非在所有容器中都可用(这确实会改变容量),而且下一个最好的东西也不是 (shrink_to_fit
),因此似乎没有一个很好的方法来始终如一地清除容器的内部内存。
C++ 标准没有要求任何标准容器释放任何内存。甚至函数 std::vector<T>::shrink_to_fit()
也只是请求缩小内存。这个函数被认为可以取代像
std::vector<T>().swap( myVector );
这个成语是用来真正释放内存的,std::vector<T>::clear()
不保证。 (事实上,std::vector<T>::clear()
被指定为保持 capacity()
不变。)你仍然可以将这个惯用语用于其他没有函数 shrink_to_fit()
的容器。