我有一个问题,我想在单个容器类中存储结构的向量。
问题是在为这些向量创建这个容器时,我浪费了资源,因为向量被复制了;没动。为什么create()
返回的临时资源未在主函数中传递给局部变量master_data
?
我假设可以使用的示例代码如下(以及coliru HERE):
#include <stdio.h>
#include <vector>
#include <stdlib.h>
// Specific data struct
typedef struct DataA {
DataA(): a(rand()),
b(rand()) {}
int a,b;
} DataA;
// Another specific data struct
typedef struct DataB {
DataB(): c(rand()),
d(rand()) {}
int c,d;
} DataB;
// Container of all relevant data
typedef struct Master {
Master(const std::vector<DataA> &a, const std::vector<DataB> &b) : data_a(std::move(a)), data_b(std::move(b)) {}
Master(const Master &rhs) : data_a(std::move(rhs.data_a)), data_b(std::move(rhs.data_b)) {}
std::vector<DataA> data_a;
std::vector<DataB> data_b;
} Master;
Master create() {
std::vector<DataA> data_a(10);
std::vector<DataB> data_b(10);
printf("data_a address inside create() : %p\n", (void*)data_a.data());
printf("data_b address inside create() : %p\n", (void*)data_b.data());
return {data_a, data_b};
}
int main()
{
Master master_data(create());
printf("data_a address outside create() : %p\n", (void*)master_data.data_a.data());
printf("data_b address outside create() : %p\n", (void*)master_data.data_b.data());
return 0;
}
答案 0 :(得分:1)
下面:
Master(const Master &rhs) : data_a(std::move(rhs.data_a)), data_b(std::move(rhs.data_b)) {}
参数是常量,这会阻止它们被移动,因为它们是不可变的。
尝试使用类似的东西:
Master(Master&& rhs) : data_a(std::move(rhs.data_a)), data_b(std::move(rhs.data_b)) {}
我放弃了const
并使用&&
增强了您的参数。
对于构造函数,您可以这样做:
Master(std::vector<DataA>&& a, std::vector<DataB>&& b) : data_a(std::move(a)), data_b(std::move(b)) {}
最后,但并非最不重要的是,您应该像这样修改您的创建函数(否则您将收到有关无法绑定的编译错误):
Master create() {
...
return {std::move(data_a), std::move(data_b)};
}
答案 1 :(得分:0)
你的构造函数:
Master(const std::vector<DataA> &a, const std::vector<DataB> &b);
接受a
和b
参数作为常量引用。您必须将其定义为接受rvalue引用,如下所示:
Master(std::vector<DataA>&& a, std::vector<DataB>&& b);
但在这种情况下,您必须指出data_a
功能中的data_b
和create()
可能会被移动:
Master create() {
std::vector<DataA> data_a(10);
std::vector<DataB> data_b(10);
printf("data_a address inside create() : %p\n", (void*)data_a.data());
printf("data_b address inside create() : %p\n", (void*)data_b.data());
return { std::move(data_a), std::move(data_b) };
}