下面的代码将数据从一个向量复制到另一个向量。如果矢量很大,那么我猜这很贵。是否可以在此处使用移动语义将数据从一个向量复制到另一个向量?
std::vector<double> newData(Shape.Size(), 0);
std::vector<double> oldData = a->getData();
std::copy(oldData.begin(), oldData.end(), newData.begin());
您可以使用算法std::move
而不是std::copy
:
std::move(oldData.begin(), oldData.end(), newData.begin());
它仍将按元素传输元素,但会移动它们。不要忘记预先分配具有正确大小的向量,以避免过多地移动元素。
是的,你可以用std::move_iterator
做到这一点。
std::copy(std::make_move_iterator(oldData.begin()),
std::make_move_iterator(oldData.end()),
newData.begin());
正如@tkausl所说,这对内置类型的vector
没有多大意义;最后在这种情况下执行复制。你可能想直接移动vector
,例如
std::vector<double> newData = std::move(oldData); // move construction
要么
newData = std::move(oldData); // move assignment
在提供的示例中,移动或复制没有区别,因为向量中的值在移动期间不执行任何空间动作(它是双倍)。
这是一个合理的例子:
using FooPtr = std::shared_ptr<Foo>;
constexpr size_t n = 100;
std::vector<FooPtr> data;
data.reserve(n);
std::generate_n(std::back_inserter(data), n, FooFactory);
std::vector<FooPtr> dst;
dst.reserve(n);
std::move(std::begin(data), std::end(data), std::back_inserter(dst));
注意
dst = std::move(data);
将更快,因为数据缓冲区将被简单地重新分配给另一个向量。
https://wandbox.org/permlink/pJnmrWYe40hLRYNE
其他答案使用make_move_iterator
。如果与其他算法一起使用,这是实用的。随着复制/移动不是很实用。
我假设你对移动语义感到困惑。如果必须保留旧数据属于旧位置,则无法使用移动语义。移动语义意味着将数据从旧移动到新移动。
格林威治标准时间18:50
#include <iostream>
#include <vector>
#include <cstdlib>
#include <ctime>
#include <cstdint>
int main()
{
std::srand(std::time(nullptr));
const int LEN_SHAPE = 1024;
std::vector<double> a;
int n = LEN_SHAPE;
while (n--)
{
a.push_back( ((double)std::rand() / RAND_MAX) * std::numeric_limits<double>::max() );
}
std::vector<double> newData(a.size(), 0);
std::vector<double> oldData( std::move( a ));
std::copy(oldData.begin(), oldData.end(), newData.begin());
}
std :: vector oldData(std :: move(a));是一个移动语义,检查此后剩下的向量a。