提问人:glades 提问时间:2/9/2023 更新时间:2/9/2023 访问量:61
将参数移动到数据成员:通过复制或 rvalue-ref 获取参数?
Moving parameter to data member: Take parameter by copy or rvalue-ref?
问:
我有一个类对象,它吞噬一个字符串并将其推入构造时的成员中(为了这个论点,它可以是任何旧成员函数)。entity
现在我至少可以通过两种方式做到这一点:我可能会接受一个 std::string 副本并将其移动到成员 () 中。但是,我也可以直接采用 rvalue-ref 并继续移动到数据成员 ()。inefficient_entity
efficient_entity
两者之间有性能差异吗?我问 bc 通过复制并让调用站点决定是否要移动或复制字符串更方便。另一种方式是,我可能需要创建一个重载集,该重载集可以增长到大量,因为我的构造函数也可以以相同的方式接受多个参数。
无论如何,这都会被优化出来还是我必须担心?
#include <string>
#include <cstdio>
struct efficient_entity
{
efficient_entity(std::string&& str)
: str_ { std::move(str) }
{ }
std::string str_;
};
struct inefficient_entity
{
inefficient_entity(std::string str)
: str_ { std::move(str) }
{ }
std::string str_;
};
int main()
{
std::string create_here = "I guarantee you this string is absolutely huge!";
efficient_entity(std::move(create_here));
inefficient_entity(std::move(create_here));
}
注意:Afaik 有一个关于 cppcon 的演讲,其中完全涵盖了这一点,但我再也找不到它了(如果有人可以给出提示,请表示感谢)。
答:
2赞
HolyBlackCat
2/9/2023
#1
按值传递会花费您多走一步。
另一方面,通过引用传递需要您编写两个函数:或 。或 N 个参数的 2 个N 个函数,或一个模板。const T &
T &&
默认情况下,我更喜欢第一个,并在应该很快的低级实用程序中使用第二个。
只有一个过载是可行的,但非常非正统。这仅为您提供一个额外的移动,这些副本必须写成(或在 C++23 中)。T &&
func(std::string(value))
func(auto(value))
这里所谓的好处是所有副本都是显式的。我只对重型类型这样做,而且只有当你喜欢这种风格时。
评论