std::set<Key,Compare,Allocator>::emplace
template< class... Args > std::pair<iterator,bool> emplace( Args&&... args ); |
(C++11 起) | |
若容器中无拥有该关键的元素,则插入以给定的 args
原位构造的新元素到容器。
细心地使用 emplace
允许在构造新元素的同时避免不必要的复制或移动操作。
准确地以与提供给 emplace
者相同的参数,通过 std::forward<Args>(args)... 转发调用新元素的构造函数。
即使容器中已有拥有该关键的元素,也可能构造元素,该情况下新构造的元素将被立即销毁。
没有迭代器或引用被非法化。
参数
args | - | 要转发给元素构造函数的参数 |
返回值
返回由指向被插入元素,或若不发生插入则为既存元素的迭代器,和指代插入是否发生的 bool (若发生插入则为 true ,否则为 false )。
异常
若任何操作抛出异常,则此函数无效果。
复杂度
与容器大小成对数。
示例
运行此代码
#include <chrono> #include <functional> #include <iomanip> #include <iostream> #include <set> #include <string> class Dew { private: int a; int b; int c; public: Dew(int _a, int _b, int _c) : a(_a), b(_b), c(_c) {} bool operator<(const Dew &other) const { if (a < other.a) return true; if (a == other.a && b < other.b) return true; return (a == other.a && b == other.b && c < other.c); } }; const int nof_operations = 120; int set_emplace() { std::set<Dew> set; for(int i = 0; i < nof_operations; ++i) for(int j = 0; j < nof_operations; ++j) for(int k = 0; k < nof_operations; ++k) set.emplace(i, j, k); return set.size(); } int set_insert() { std::set<Dew> set; for(int i = 0; i < nof_operations; ++i) for(int j = 0; j < nof_operations; ++j) for(int k = 0; k < nof_operations; ++k) set.insert(Dew(i, j, k)); return set.size(); } void timeit(std::function<int()> set_test, std::string what = "") { auto start = std::chrono::system_clock::now(); int setsize = set_test(); auto stop = std::chrono::system_clock::now(); std::chrono::duration<double, std::milli> time = stop - start; if (what.size() > 0 && setsize > 0) { std::cout << std::fixed << std::setprecision(2) << time.count() << " ms for " << what << '\n'; } } int main() { set_insert(); timeit(set_insert, "insert"); timeit(set_emplace, "emplace"); timeit(set_insert, "insert"); timeit(set_emplace, "emplace"); }
可能的输出:
638.45 ms for insert 619.44 ms for emplace 609.43 ms for insert 652.55 ms for emplace
参阅
(C++11) |
使用提示原位构造元素 (公开成员函数) |
插入元素或结点 (C++17 起) (公开成员函数) |