rec*_*onn 14 c++ vector perfect-forwarding c++11 list-initialization
我注意到当移动更适用时,std::vector 的聚合 列表初始化执行复制初始化。同时,多个 emplace_backs 做我想做的。
我只能想出这个编写模板函数的不完美解决方案init_emplace_vector
。不过,它仅适用于非显式单值构造函数。
template <typename T, typename... Args>
std::vector<T> init_emplace_vector(Args&&... args)
{
std::vector<T> vec;
vec.reserve(sizeof...(Args)); // by suggestion from user: eerorika
(vec.emplace_back(std::forward<Args>(args)), ...); // C++17
return vec;
}
Run Code Online (Sandbox Code Playgroud)
我真的需要使用 emplace_back来尽可能有效地初始化 std::vector 吗?
// an integer passed to large is actually the size of the resource
std::vector<large> v_init {
1000, // instance of class "large" is copied
1001, // copied
1002, // copied
};
std::vector<large> v_emplaced;
v_emplaced.emplace_back(1000); // moved
v_emplaced.emplace_back(1001); // moved
v_emplaced.emplace_back(1002); // moved
std::vector<large> v_init_emplace = init_emplace_vector<large>(
1000, // moved
1001, // moved
1002 // moved
);
Run Code Online (Sandbox Code Playgroud)
类large
产生关于复制/移动的信息(下面的实现),所以我的程序的输出是:
- initializer
large copy
large copy
large copy
- emplace_back
large move
large move
large move
- init_emplace_vector
large move
large move
large move
Run Code Online (Sandbox Code Playgroud)
我的实现large
只是一个可复制/可移动类型,其中包含一个大型资源,在复制/移动时发出警告。
- initializer
large copy
large copy
large copy
- emplace_back
large move
large move
large move
- init_emplace_vector
large move
large move
large move
Run Code Online (Sandbox Code Playgroud)
通过使用保留,没有复制或移动。只large::large(std::size_t)
调用构造函数。真正的阵地。
eer*_*ika 11
我可以聚合初始化 std::vector ...
No.std::vector
不是聚合,所以它不能被聚合初始化。
您可能指的是列表初始化,在这种情况下:
我可以[list-initialise] std::vector 完美转发元素吗?
不。列表初始化使用std::initializer_list
构造函数并std::initializer_list
复制其参数。
您init_emplace_vector
似乎是一个不错的解决方案,尽管可以通过在放置元素之前保留内存来改进它。