首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >对已构造的对象使用std::move与emplace_back()的C++11 push_back()的效率

对已构造的对象使用std::move与emplace_back()的C++11 push_back()的效率
EN

Stack Overflow用户
提问于 2014-11-11 16:41:26
回答 2查看 30.6K关注 0票数 101

在C++11中,emplace_back()通常比push_back()更受欢迎(就效率而言),因为它允许就地构造,但是当将与已经构造的对象一起使用时,是否仍然是这种情况?

例如,在下面这样的情况下,emplace_back()仍然是首选的吗?

代码语言:javascript
复制
std::string mystring("hello world");
std::vector<std::string> myvector;

myvector.emplace_back(mystring);
myvector.push_back(std::move(mystring));
// (of course assuming we don't care about using the value of mystring after)

此外,在上面的示例中执行以下操作是否有任何好处:

代码语言:javascript
复制
myvector.emplace_back(std::move(mystring));

或者,这里的迁移是完全多余的,还是没有任何影响?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2014-11-11 17:27:06

让我们看看您提供的不同调用有什么作用:

  1. emplace_back(mystring):这是新元素的就地构造,使用您提供的任何参数。由于您提供了一个左值,因此该就地构造实际上是一个复制构造,即这与调用push_back(mystring)

相同

这称为移动插入,在std::string的情况下是一个就地move-construction.

  1. emplace_back(std::move(mystring)):这又是一个使用您提供的参数的就地构造。由于该参数是一个右值,因此它调用std::string的移动构造函数,即它是一个原地移动构造,如2.

换句话说,如果用一个T类型的参数调用,无论是右值还是左值,emplace_backpush_back都是等价的。

但是,对于任何其他参数,emplace_back将赢得竞争,例如,在vector<string>中使用char const*

  1. emplace_back("foo")为in-place-construction.

调用std::string(char const*)

  1. push_back("foo")首先必须调用std::string(char const*)进行匹配函数签名所需的隐式转换,然后调用移动插入,如上例2所示。因此,它等同于push_back(string("foo"))
票数 128
EN

Stack Overflow用户

发布于 2014-11-11 17:55:00

emplace_back获取一个右值引用列表,并尝试直接在适当的位置构造一个容器元素。您可以使用容器元素构造函数支持的所有类型调用emplace_back。当为不是右值引用的参数调用emplace_back时,当参数和容器元素属于同一类型时,它将“后退”到正常引用,并且至少会调用复制构造函数列表。在你的例子中,'myvector.emplace_back(mystring)‘应该复制字符串,因为编译器无法知道参数myvector是可移动的。因此,插入std::move,让您获得所需的好处。对于已经构造的元素,push_back应该和emplace_back一样工作。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/26860749

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档