C++ STL中的multiset::emplace()
C++ STL(标准模板库)是一个重要的C++标准库。multiset是其中的一种容器,可以看作是一组有序的元素集合。multiset::emplace()是C++ STL中一个成员函数,它可以在multiset容器中插入元素,同时保证有序性。本篇文章将详细介绍multiset::emplace()函数的用法。
multiset容器
multiset是一个由元素组成的容器,它可以存储任意类型的数据。multiset内部是有序的,它使用一个比较函数进行排序,可以自定义比较函数。
multiset容器的定义方式如下:
#include<set>
std::multiset<T, Compare> ms;
其中,T表示元素的类型,Compare表示比较函数。如果不指定Compare,则使用默认的“小于”比较。multiset内部使用红黑树算法进行排序,时间复杂度为O(log N),其中N为元素个数。
下面是一个multiset容器的示例:
#include<set>
#include<iostream>
int main()
{
std::multiset<int> ms;
ms.insert(5);
ms.insert(3);
ms.insert(8);
for (auto it=ms.begin(); it!=ms.end(); ++it)
std::cout << *it << " ";
std::cout << std::endl;
return 0;
}
输出结果为:
3 5 8
multiset::emplace()
multiset::emplace()是一个成员函数,它可以在multiset容器中插入元素,同时保证有序性。与insert()函数不同的是,emplace()函数可以直接在容器中构造一个元素,而不需要先构造一个临时对象,然后再插入到容器中。
multiset::emplace()函数的定义方式如下:
template <class... Args>
iterator emplace(Args&&... args);
其中,Args表示元素的构造参数。emplace()函数接受任意数量的构造参数,并将它们传递给元素的构造函数来构造元素。该函数返回一个迭代器,指向插入的元素。
下面是一个multiset::emplace()函数的示例:
#include<set>
#include<iostream>
struct foo
{
int id;
std::string name;
foo(int i, const std::string& s): id(i), name(s){ }
bool operator<(const foo& rhs) const { return id<rhs.id; }
};
int main()
{
std::multiset<foo> ms;
ms.emplace(2, "two");
ms.emplace(1, "one");
ms.emplace(3, "three");
for (auto& f:ms)
std::cout << f.id << ":" << f.name << " ";
std::cout << std::endl;
return 0;
}
输出结果为:
1:one 2:two 3:three
在上面的示例中,我们定义了一个名为foo的结构体。foo有两个成员变量id和name,它们分别表示元素的标识和名称。foo还包含一个小于号运算符,用于比较元素的id。
我们使用multiset容器来存储foo元素,使用emplace()函数在容器中插入元素,构造时提供元素的id和name。最后,使用迭代器遍历容器,输出元素的id和name。
多参数形式的emplace()
multiset::emplace()函数还可以有多个参数的形式,这样可以提供更多的初始化参数。例如,如果元素是一个类对象,有多个成员变量,就可以使用多个参数形式的emplace()来初始化元素。
下面是一个多参数形式的emplace()函数的示例:
#include<set>
#include<iostream>
class foo
{
public:
foo(int id, const std::string& name, double score):
id_(id), name_(name), score_(score)
{
std::cout << "constructing foo(id=" << id_ << ", name=" << name_ << ", score=" << score_ << ")" << std::endl;
}
~foo()
{
std::cout << "destroying foo(id=" << id_ << ", name=" << name_ << ", score=" << score_ << ")" << std::endl;
}
bool operator<(const foo& rhs) const { return id_<rhs.id_; }
private:
int id_;
std::string name_;
double score_;
};
int main()
{
std::multiset<foo> ms;
ms.emplace(2, "Tom", 88.5);
ms.emplace(1, "Alice", 95.0);
ms.emplace(3, "Bob", 79.0);
for (auto& f:ms)
std::cout << f << " ";
std::cout << std::endl;
return 0;
}
在上面的示例中,我们定义了一个名为foo的类,它有三个成员变量id、name和score。我们在构造函数中输出一行文本,以显示调用构造函数的过程。
我们使用multiset容器来存储foo元素,使用多参数形式的emplace()函数在容器中插入元素,构造时提供元素的id、name和score。最后,使用迭代器遍历容器,输出元素的id、name和score。
由于foo类定义了析构函数,在程序结束时,对于每个元素调用析构函数,输出一行文本,以显示调用析构函数的过程。
总结
本文介绍了multiset::emplace()函数的用法。与insert()函数不同的是,emplace()函数可以直接在容器中构造一个元素,而不需要先构造一个临时对象,然后再插入到容器中。emplace()函数接受任意数量的构造参数,并将它们传递给元素的构造函数来构造元素。该函数返回一个迭代器,指向插入的元素。多参数形式的emplace()函数可以提供更多的初始化参数。