【发布时间】:2016-04-21 10:28:50
【问题描述】:
使用push_back/emplace_back(罕见的push_front/emplace_front 甚至push_after/emplace_after)我几乎可以从STL 中填充任何容器。甚至是非默认可构造元素的容器。减小尺寸只需要元素的析构函数(此外,容器必须要求元素为Destructible)。但我不能简单地使用resize(如果存在)来减小非默认可构造元素容器的大小。相反,我必须使用一种解决方法,即使对于它们中最不严格的(特殊功能):std::list。
#include <list>
#include <cstdlib>
int
main()
{
// construct
std::list< std::reference_wrapper< int > > l;
// fill
int i{};
l.emplace_back(i);
int j{};
l.emplace_back(j);
// save intermediate state for future
std::size_t const size = l.size();
// continue appending
int k{};
l.emplace_back(k);
// now I want to rollback to saved state
//l.resize(size); // just need to call the destructors, but illegal due to not default constructible value_type
// so I have to use a workaround
for (std::size_t s = l.size(); size < s; --s) {
l.pop_back();
}
return EXIT_SUCCESS;
}
即使是一元 std::list::resize 版本 std::list::value_type 也应该是 DefaultInsertable。
我希望一元 resize(std::size_t) 仅用于上述类型的容器中的“减小大小”目的。如果value_type 不是DefaultConstructible,则可以禁止resize(std::size_t, value_type = value_type()) 参与重载决议(例如,使用基类调度)以支持resize(std::size_t)/resize(std::size_t, value_type) 对。如果所需的大小大于当前大小,例如resize(std::size_t),则应该抛出std::bad_alloc。有可能设计吗?
【问题讨论】:
-
如果你想减小尺寸,你可以使用擦除或拼接之类的东西来拉出你不想要的元素吗?
-
@templatetypedef 一方面
erase(甚至std::deque::erase)会导致非擦除元素的引用和迭代器过度失效,另一方面erase需要一个迭代器/迭代器pair - 它更详细,然后只是resize(123);。 -
虽然,对于
std::list,没有超出范围的迭代器会失效。
标签: c++ c++11 stl containers default-constructor