2014-10-30 117 views
0

每当我需要创建一个非复制构造对象的数组时,我偶尔会遇到这种情况。例如:为什么std :: vector fill构造函数不能启用安装?

std::vector<std::thread> thread_pool(NUM_CORES, std::thread(some_function)); 

这样很方便。但是,唉,std::vector填充构造函数似乎没有任何R值的支持。它被定义为:

vector( 
     size_type count, 
     const T& value, 
     const Allocator& alloc = Allocator() 
); 

但它会极为方便有:

vector( 
     size_type count, 
     T&& value, 
     const Allocator& alloc = Allocator() 
); 

然后该载体可在内部分配必要的缓冲器大小,并移动-构造每个元件与放置新。

但是...... C++ 11标准(显然甚至是C++ 14标准)不提供这种功能。所以,现在 - 当我有一个线程向量时,我不得不说:

std::vector<std::unique_ptr<std::thread>> thread_pool(NUM_CORES); 
/* now loop over vector and initialize elements one by one */ 

有没有什么理由将这种能力排除在外?有危险吗?或者我没有看到一些问题?

+2

一个更好的方式“解决办法”将是' std :: vector v; v.reserve(NUM_CORES); for(...)v.emplace_back(...);'。不需要指针。答案可能是“因为从来没有人打算提出这个问题”。 – stefan 2014-10-30 18:13:53

+4

在移动构造或赋值之后,右值引用保持有效但未知的状态。你真正想要的是能够有像emplace_back这样的可变构造函数。但是如果任何T构造函数的参数都是右值,那么右值将再次提升。 @stefan解决方法就是我通常所做的。 – galop1n 2014-10-30 18:16:03

+4

大声笑你如何建议移动 - 从一个原始参数构造多个元素? – 2014-10-30 18:22:14

回答

4

你提出什么是不可行的,因为,就其本质而言,移动是一个国家从一个对象转移到一个其他物体。通过同时将状态从一个状态移动到全部状态,不能构造对象。

星际之门的宇宙通过引入能够同时打开一个虫洞到银河系的每个门的能力而违反了这条规则,这根本没有意义,并且真的让我恼火。不要那个人!

矢量构造看起来像这样:

template <typename T> 
template <typename Args...> 
std::vector<T>::vector(const size_t n, Args&&... args); 

&hellip;继emplace模型可能工作,但我担心,这将是很容易得到一个模棱两可的超负荷由于现有的构造函数的绝对数量为std::vector<T>。我怀疑这就是为什么它没有完成,除了事实并非真的有必要。

因为,现在,你可以通过安放一个在时间,这不分,很可能是因为高性能的,你能指望得到变通办法:

std::vector<std::thread> v; 
v.reserve(NUM_CORES); 
for (/*...*/) 
    v.emplace_back(/*...*/); 
相关问题