gpt4 book ai didi

c++ - 何时使用 move 构造函数/赋值

转载 作者:塔克拉玛干 更新时间:2023-11-02 23:06:33 27 4
gpt4 key购买 nike

我搜索过但找不到“何时”使用它们的答案。我一直听说它很好,因为它为我节省了额外的拷贝。我到处把它放在我上过的每个类(class)中,但有些人似乎对某些类(class)没有意义:我已经阅读了无数关于 LValues 和 RValues 以及 std::move vs. std::copy vs. memcpy 的教程与 memmove 等。甚至阅读 throw() 但我也不确定何时使用它。

我的代码如下:

struct Point
{
int X, Y;

Point();
Point(int x, int y);
~Point();

//All my other operators here..
};

然后我有一个类数组(类似 RAII 的东西):

class PA
{
private:
std::vector<Point> PointsList;

public:
PA();
//Variadic Template constructor here..
~PA();
//Operators here..
};

我应该使用 move 构造函数和复制构造函数吗?我在 Point Class 中有它,但感觉很奇怪,所以我将其删除。然后我在 PA 课上有了它,但我认为它不会做任何事情,所以我也删除了它。然后在我的位图类中,我的编译器提示有指针成员但没有重载,所以我做了:

//Copy Con:
BMPS::BMPS(const BMPS& Bmp) : Bytes(((Bmp.width * Bmp.height) != 0) ? new RGB[Bmp.width * Bmp.height] : nullptr), width(Bmp.width), height(Bmp.height), size(Bmp.size), DC(0), Image(0)
{
std::copy(Bmp.Bytes, Bmp.Bytes + (width * height), Bytes);
BMInfo = Bmp.BMInfo;
bFHeader = Bmp.bFHeader;
}

//Move Con:
BMPS::BMPS(BMPS&& Bmp) : Bytes(nullptr), width(Bmp.width), height(Bmp.height), size(Bmp.size), DC(0), Image(0)
{
Bmp.Swap(*this);
Bmp.Bytes = nullptr;
}

//Assignment:
BMPS& BMPS::operator = (BMPS Bmp)
{
Bmp.Swap(*this);
return *this;
}

//Not sure if I need Copy Assignment?

//Move Assignment:
BMPS& BMPS::operator = (BMPS&& Bmp)
{
this->Swap(Bmp);
return *this;
}

//Swap function (Member vs. Non-member?)
void BMPS::Swap(BMPS& Bmp) //throw()
{
//I was told I should put using std::swap instead here.. for some ADL thing.
//But I always learned that using is bad in headers.
std::swap(Bytes, Bmp.Bytes);
std::swap(BMInfo, Bmp.BMInfo);
std::swap(width, Bmp.width);
std::swap(height, Bmp.height);
std::swap(size, Bmp.size);
std::swap(bFHeader, Bmp.bFHeader);
}

这是正确的吗?我做错事了吗?我需要 throw() 吗?我的赋值和 move 赋值运算符实际上应该是一样的吗?我需要复制作业吗?啊这么多问题 :c 我问的最后一个论坛无法回答所有问题,所以我很困惑。最后我应该对字节使用 unique_ptr 吗? (这是一个字节/像素数组。)

最佳答案

Scott Meyer's blog 上有一些很棒的想法:

First, not all copy requests can be replaced by moves. Only copy requests for rvalues are eligible for the optimization. Second, not all types support move operations that are more efficient than copying operations. An example is a std::array. Third, even types that support efficient move operations may support them only some of the time. Case in point: std::string. It supports moves, but in cases where std::string is implemented using SSO (the small string optimization), small strings are just as expensive to move as to copy!

或许,您可以相应地对类型进行分类,然后决定哪些类型需要 move 语义。请注意,编译器自动生成 move ctors/赋值运算符存在限制,因此建议您牢记这些。当您明确指定 move 成员时,这会有所帮助。

对于没有明确指定 move 成员的类,有一些麻烦的地方。还存在显式/隐式删除 move 成员的问题,该成员禁止从右值 进行复制。可以在 Stroustrup 题为 To Move or Not to Move 的论文中找到关于隐式生成 move 成员的问题的一个非常有值(value)的来源。 .

关于 move 语义的异常处理,我建议 Dave Abraham 的帖子 Exceptionally Moving .

我会在有空的时候试着用一些例子来回答这个问题。目前,希望上述链接能帮助您入门。

关于c++ - 何时使用 move 构造函数/赋值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11077103/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com