一、前言

和 map、multimap 容器不同,应用 set 容器存储的各个键值对,要求键 key 和值 value 必须相等。如下:

{<'a', 'a'>, <'b', 'b'>, <'c', 'c'>}

不反对存储键和值不相等的键值对。因而在应用set容器时,只须要为其提供各键值对中的value值即可。set容器和map容器一样,会自行依据键的大小对存储的键值对进行排序,在set容器中,实际上也是依据value值进行排序。
set 容器存储的各个元素的值必须各不相同。须要留神的是:在语法上set容器并没有强制对存储元素的类型做const润饰,因而set容器中存储的元素的值是能够批改的。然而,C++ 规范为了避免用户批改容器中元素的值,对所有可能会实现此操作的行为做了限度,使得在失常状况下,用户是无奈做到批改 set 容器中元素的值的
留神:间接批改set容器中的已存储的元素的值,可能会毁坏set容器中元素的有序性。最正确的批改 set 容器中元素值的做法是:先删除该元素,而后再增加一个批改后的元素。应用set容器,须要

#include <set>

1、set容器类模板的定义

template < class T,     // 键 key 和值 value 的类型           class Compare = less<T>,  // 指定 set 容器外部的排序规定           class Alloc = allocator<T>  // 指定分配器对象的类型           > class set;

因为键和值的类型是一样的,因而这里只有3个参数,大多数状况下,主须要用到其中的前2个参数。

二、创立set容器的办法

常见的创立 set 容器的办法,大抵有以下 5 种。

①std::set<std::string> myset;②std::set<std::string> myset{"1","2","3"};③std::set<std::string> copyset(myset);④std::set<std::string> myset{"1","2","3"};std::set<std::string> copyset(++myset.begin(), myset.end());⑤std::set<std::string,std::greater<string> > myset{"1","2","3"};

①默认构造函数,创立空的set容器,会对存储的 string 类型元素做升序排序
②在创立 set 容器的同时,对其进行初始化
③通过拷贝(复制)构造函数,实现在创立新 set 容器的同时,将已有 set 容器中存储的所有元素全副复制到新 set 容器中,等价于std::set<std::string> copyset = myset;C++ 11 规范还为 set 类模板新增了挪动构造函数,其性能是实现创立新 set 容器的同时,利用长期的 set 容器为其初始化,如下:

set<string> retSet() {    std::set<std::string> myset{ "1","2","3" };    return myset;   //返回值是一个长期 set 容器,因而在初始化 copyset 容器时,其外部调用的是 set 类模板中的挪动构造函数,而非拷贝构造函数。}std::set<std::string> copyset(retSet());//等价于 std::set<std::string> copyset = retSet();

④set 类模板取已有 set 容器中的局部元素,来初始化新 set 容器
⑤、批改 set 容器中的排序规定形式

三、办法

这里不列举迭代器、插入和删除相干的办法。

办法性能
empty()若容器为空,则返回 true;否则 false
size()返回以后 set 容器中存有元素的个数
max_size()返回 set 容器所能包容元素的最大个数,不同的操作系统,其返回值亦不雷同
count(val)在以后 set 容器中,查找值为 val 的元素的个数,并返回。留神,因为 set 容器中各元素的值是惟一的,因而该函数的返回值最大为 1

四、实例

1、创立set容器

形式1

std::set<std::string> myset;std::cout << "myset size: " << myset.size() << std::endl;

形式2

std::set<std::string> myset1{                             "who are you",                            "i am lin",                            "i am wu",                            "i am ouyang"};std::cout << "myset1 size: " << myset1.size() << std::endl;std::set<std::string>::iterator setIter = myset1.begin();for (; setIter != myset1.end(); setIter++){    std::cout << "myset1 :" << *setIter << std::endl;}

形式3

std::set<std::string> myset2(myset1);std::cout << "myset2 size: " << myset2.size() << std::endl;setIter = myset2.begin();for (; setIter != myset2.end(); setIter++){    std::cout << "myset2 :" << *setIter << std::endl;}

挪动构造函数形式

set<string> RemoveStructureSet(){    std::set<std::string> myset{                             "who are you",                            "i am wen",                            "i am li" };    return myset;}std::set<std::string> myset3(RemoveStructureSet()); //等价于 std::set<std::string> myset3 = RemoveStructureSet();setIter = myset3.begin();for (; setIter != myset3.end(); setIter++){    std::cout << "myset3 :" << *setIter << std::endl;}

形式4

std::set<std::string> myset4(++myset.begin(), --myset.end()); setIter = myset4.begin();for (; setIter != myset4.end(); setIter++){    std::cout << "myset4 :" << *setIter << std::endl;}

形式5

std::set<std::string, std::greater<string> > myset5{                            "who are you",                            "i am lin",                            "i am wu",                            "i am ouyang" };setIter = myset5.begin();for (; setIter != myset5.end(); setIter++){    std::cout << "myset5 :" << *setIter << std::endl;}

后果如下: