具有已构建对象的std :: move与emplace_back()的C ++ 11 push_back()效率 [英] Efficiency of C++11 push_back() with std::move versus emplace_back() for already constructed objects

查看:313
本文介绍了具有已构建对象的std :: move与emplace_back()的C ++ 11 push_back()效率的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在C ++ 11中,emplace_back()(就效率而言)通常比push_back()更可取,因为它允许就地构建,,但在已将push_back(std::move())与已构造的对象?

In C++11 emplace_back() is generally preferred (in terms of efficiency) to push_back() as it allows in-place construction, but is this still the case when using push_back(std::move()) with an already-constructed object?

例如,在以下情况下,仍首选emplace_back()吗?

For instance, is emplace_back() still preferred in cases like the following?

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)

此外,在上面的示例中,这样做还有什么好处?

Additionally, is there any benefit in the above example to instead doing:

myvector.emplace_back(std::move(mystring));

还是这里的举动是完全多余的,还是没有效果?

or is the move here entirely redundant, or has no effect?

推荐答案

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

Let's see what the different calls that you provided do:

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

  1. emplace_back(mystring): This is an in-place construction of the new element with whatever argument you provided. Since you provided an lvalue, that in-place construction in fact is a copy-construction, i.e. this is the same as calling push_back(mystring)

push_back(std::move(mystring)):这称为移动插入,在std :: string的情况下,它是就地移动构造.

push_back(std::move(mystring)): This calls the move-insertion, which in the case of std::string ist an in-place move-construction.

emplace_back(std::move(mystring)):这也是使用您提供的参数的就地构造.由于该参数是一个右值,因此它调用std::string的move-constructor,即像2中那样是一个就地move-construction.

emplace_back(std::move(mystring)): This is again an in-place construction with the arguments you provided. Since that argument is an rvalue, it calls the move-constructor of std::string, i.e. it is an in-place move-construction like in 2.

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

In other words, if called with one argument of type T, be it an rvalue or lvalue, emplace_back and push_back are equivalent.

但是,对于任何其他参数,emplace_back都会赢得比赛,例如在vector<string>中使用char const*:

However, for any other argument(s), emplace_back wins the race, for example with a char const* in a vector<string>:

  1. emplace_back("foo")调用string::string(char const*)进行就地构建.

push_back("foo")首先必须调用string::string(char const*)进行与函数签名匹配的隐式转换,然后再进行如上情况2的移动插入.因此,它等效于push_back(string("foo"))

push_back("foo") first has to call string::string(char const*) for the implicit conversion needed to match the function's signature, and then a move-insertion like case 2. above. Therefore it is equivalent to push_back(string("foo"))

这篇关于具有已构建对象的std :: move与emplace_back()的C ++ 11 push_back()效率的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆