[C++] push_back vs emplace_back
总结:
push_back
分为两步:先创建一个临时的构造器,然后将这个临时构造器移动或者拷贝到目标容器中。
emplace_back
仅有一步:直接在目标容器的目标位置,原地创建构造器即可,无需移动或者拷贝操作。
关键观点:函数void emplace_back(Type&& _Val)
完全等价于push_back(Type&& _Val)
,没有意义,因为是多余的。函数void emplace_back(Args&&...)
特别有用,它无需采用变量类型value_type
,而是采用可变参数列表,因此,这意味着可以完美地转发参数并直接将对象构造到容器中,而无需任何临时操作。
原文如下:
高赞回复1
In addition to what visitor said :
The function
void emplace_back(Type&& _Val)
provided by MSCV10 is non conforming and redundant, because as you noted it is strictly equivalent topush_back(Type&& _Val)
.But the real C++0x form of
emplace_back
is really useful:void emplace_back(Args&&...)
;Instead of taking a
value_type
it takes a variadic list of arguments, so that means that you can now perfectly forward the arguments and construct directly an object into a container without a temporary at all.That’s useful because no matter how much cleverness RVO and move semantic bring to the table there is still complicated cases where a
push_back
is likely to make unnecessary copies (or move). For example, with the traditional insert() function of a std::map, you have to create a temporary, which will then be copied into a std::pair<Key, Value>, which will then be copied into the map :std::map<int, Complicated> m; int anInt = 4; double aDouble = 5.0; std::string aString = "C++"; // cross your finger so that the optimizer is really good(形参为value_type) m.insert(std::make_pair(4, Complicated(anInt, aDouble, aString))); // should be easier for the optimizer (形参为可变参数列表) m.emplace(4, anInt, aDouble, aString);
高赞回复2
// constructs the elements in place. emplace_back("element"); //It will create new object and then copy(or move) its value of arguments. push_back(explicitDataType{"element"});
高赞回复3
Specific use case for
emplace_back
: If you need to create a temporary object which will then be pushed into a container, use emplace_back instead of push_back. It will create the object in-place within the container.Notes:
push_back
in the above case will create a temporary object and move it into the container. However, in-place construction used foremplace_back
would be more performant than constructing and then moving the object (which generally involves some copying).- In general, you can use
emplace_back
instead ofpush_back
in all the cases without much issue. (See exceptions)
推荐阅读
-
ubuntu下VS code如何调试C++代码
-
vs2015开发人员命令提示工具 查看C++类对象模型
-
VS2015中不同开发环境设置转换(C#->C++等)
-
C++雾中风景9:emplace_back与可变长模板
-
Ubuntu下安装并配置VS Code编译C++的方法
-
vs2017 如何定位C++内存泄漏
-
[原创]c/c++在vc6,vs(visual studio2010),codeblocks,wxDev c++中应用sqlite3 API笔记
-
【C++】VS2015/VS2017连接Mysql数据库教程
-
Windows10下VS2017编译MQTT C与编译MQTT C++
-
VS2017中C++打包DLL库在CSharp(C#)中调用