c++ - 在这种情况下 std::move 是否矫枉过正?
问题描述
我想知道std::move()
在这个例子中使用它是否比简单地复制它是过度杀伤或计算成本更高?我真的很想知道。
class Student
{
private:
std::string _studentName;
int _studentGrade;
public:
Student() : _studentName("No Name"), _studentGrade(0) {}
std::string Name() const { return _studentName; }
void Name(std::string x) { _studentName = std::move(x); }
int Grade() const { return _studentGrade; }
void Grade(int x) { _studentGrade = std::move(x); }
};
解决方案
阅读F.call 的核心指南:参数传递,我们可以得出一些建议。
仅当您想针对右值进行优化时才使用 move。如果您发现它可以提高性能,则由您决定。
您可以按值接收然后移动,因为它优化了对您的设置器的右值调用,但它使左值感到悲观。这是因为std::string
从 const 引用复制时将重用其存储并且不会导致不必要的分配。当没有 SSO 可能时,复制到 value 参数总是最终分配。
首选方法,尤其是对于 setter,是使用 const 引用,并在将右值传递给 setter 时添加右值引用重载:
class Student
{
private:
std::string _studentName;
int _studentGrade;
public:
Student() : _studentName("No Name"), _studentGrade(0) {}
std::string_view Name() const { return _studentName; }
void Name(std::string const& x) { _studentName = x; }
// add this when you need to optimize for rvalues.
// optimizing for rvalues is not always needed.
// They can speedup quite a bit when actually needed.
void Name(std::string&& x) { _studentName = std::move(x); }
// int is a trivial type, so move does nothing. No move needed.
int Grade() const { return _studentGrade; }
void Grade(int x) { _studentGrade = x; }
}
对于 int,std::move
不会做任何事情,它仍然是一个副本。只需按值取值并按值返回即可。
但是,您能做的最好的事情要简单得多:
class Student
{
public:
std::string studentName;
int studentGrade;
};
由于您的设置器不强制执行任何不变量,因此您最好使用公共成员。您不需要重载和引用,因为std::string
它会为您实现。
推荐阅读
- python - Pandas - 用 Nan 替换重复项并保持行
- c++ - 如何在较新的 Qt 和 QtCreator 中安装和调试较旧的 Qt 版本?
- sql - 未在 Insert-Select 上收集的统计信息
- javascript - v-如果不更新导航栏
- function - 如何在 Haskell 中编写函数的类型签名
- css - 如何使用 css 创建带有翅膀或标签的 div 框
- mysql - 当表是“productDef”时,为什么 Spring Data / Hibernate 会查询表“product_def”?
- c - 为什么在这种二进制除法的情况下左移商?
- markdown - 使用 Pandoc 将部分分隔符插入 Markdown ePub
- vue.js - Vue.js + Element UI + el-popover - dynamically changing trigger doesn't work