• C++ STL set/multset


      set容器内的元素会被自动排序,set与map不同,set中的元素即是键值又是实值,set不允许两个元素有相同的键值。不能通过set的迭代器去修改set元素,原因是修改元素会破坏set组织。当对容器中的元素进行插入或者删除时,操作之前的所有迭代器在操作之后依然有效。

      multiset特性及用法和set完全相同,唯一的差别在于它允许键值重复。

      set和multiset的底层实现是一种高效的平衡二叉树,即红黑树(Red-Black Tree)。

    以下代码涉及的内容:

    1、set容器中,元素类型为基本类型,如何让set按照用户意愿来排序?

    2、set容器中,如何让元素类型为自定义类型?

    3、set容器的insert函数的返回值为什么类型?

      1 #include <iostream>
      2 #include <string>
      3 #include <set>
      4 using namespace std;
      5 
      6 /* 仿函数CompareSet,在test02使用 */
      7 class CompareSet
      8 {
      9 public:
     10     //从大到小排序
     11     bool operator()(int v1, int v2)
     12     {
     13         return v1 > v2;
     14     }
     15     //从小到大排序
     16     //bool operator()(int v1, int v2)
     17     //{
     18     //    return v1 < v2;
     19     //}
     20 };
     21 
     22 /* Person类,用于test03 */
     23 class Person
     24 {
     25     friend ostream &operator<<(ostream &out, const Person &person);
     26 public:
     27     Person(string name, int age)
     28     {
     29         mName = name;
     30         mAge = age;
     31     }
     32 public:
     33     string mName;
     34     int mAge;
     35 };
     36 
     37 ostream &operator<<(ostream &out, const Person &person)
     38 {
     39     out << "name:" << person.mName << " age:" << person.mAge << endl;
     40     return out;
     41 }
     42 
     43 /* 仿函数ComparePerson,用于test03 */
     44 class ComparePerson
     45 {
     46 public:
     47     //名字大的在前面,如果名字相同,年龄大的排前面
     48     bool operator()(const Person &p1, const Person &p2)
     49     {
     50         if (p1.mName == p2.mName)
     51         {
     52             return p1.mAge > p2.mAge;
     53         }
     54         return p1.mName > p2.mName;
     55     }
     56 };
     57 
     58 /* 打印set类型的函数模板 */
     59 template<typename T>
     60 void PrintSet(T &s)
     61 {
     62     for (T::iterator iter = s.begin(); iter != s.end(); ++iter)
     63         cout << *iter << " ";
     64     cout << endl;
     65 }
     66 
     67 void test01()
     68 {
     69     //set容器默认从小到大排序
     70     set<int> s;
     71     s.insert(10);
     72     s.insert(20);
     73     s.insert(30);
     74 
     75     //输出set
     76     PrintSet(s);
     77     //结果为:10 20 30
     78 
     79     /* set的insert函数返回值为一个对组(pair)。
     80        对组的第一个值first为set类型的迭代器:
     81        1、若插入成功,迭代器指向该元素。
     82        2、若插入失败,迭代器指向之前已经存在的元素
     83 
     84        对组的第二个值seconde为bool类型:
     85        1、若插入成功,bool值为true
     86        2、若插入失败,bool值为false
     87     */
     88     pair<set<int>::iterator, bool> ret = s.insert(40);
     89     if (true == ret.second)
     90         cout << *ret.first << " 插入成功" << endl;
     91     else
     92         cout << *ret.first << " 插入失败" << endl;
     93 }
     94 
     95 void test02()
     96 {
     97     /* 如果想让set容器从大到小排序,需要给set容
     98        器提供一个仿函数,本例的仿函数为CompareSet
     99     */
    100     set<int, CompareSet> s;
    101     s.insert(10);
    102     s.insert(20);
    103     s.insert(30);
    104     
    105     //打印set
    106     PrintSet(s);
    107     //结果为:30,20,10
    108 }
    109 
    110 void test03()
    111 {
    112     /* set元素类型为Person,当set元素类型为自定义类型的时候
    113        必须给set提供一个仿函数,用于比较自定义类型的大小,
    114        否则无法通过编译 
    115     */
    116     set<Person,ComparePerson> s;
    117     s.insert(Person("John", 22));
    118     s.insert(Person("Peter", 25));
    119     s.insert(Person("Marry", 18));
    120     s.insert(Person("Peter", 36));
    121 
    122     //打印set
    123     PrintSet(s);
    124 }
    125 
    126 int main(void)
    127 {
    128     //test01();
    129     //test02();
    130     //test03();
    131     return 0;
    132 }
    使用set容器需要注意的细节

    以下代码涉及的内容:

    1、multiset容器的insert函数返回值为什么? 

     1 #include <iostream>
     2 #include <set>
     3 using namespace std;
     4 
     5 /* 打印set类型的函数模板 */
     6 template<typename T>
     7 void PrintSet(T &s)
     8 {
     9     for (T::iterator iter = s.begin(); iter != s.end(); ++iter)
    10         cout << *iter << " ";
    11     cout << endl;
    12 }
    13 
    14 void test(void)
    15 {
    16     multiset<int> s;
    17     s.insert(10);
    18     s.insert(20);
    19     s.insert(30);
    20     
    21     //打印multiset
    22     PrintSet(s);
    23 
    24     /* multiset的insert函数返回值为multiset类型的迭代器,
    25        指向新插入的元素。multiset允许插入相同的值,因此
    26        插入一定成功,因此不需要返回bool类型。
    27     */
    28     multiset<int>::iterator iter = s.insert(10);
    29     
    30     cout << *iter << endl;    
    31 }
    32 
    33 int main(void)
    34 {
    35     test();
    36     return 0;
    37 }
    使用multiset容器需要注意的细节
    set构造函数
    函数 功能
    set<T> st set默认构造函数
    mulitset<T> mst multiset默认构造函数
    set(const set &st) 拷贝构造函数
    set赋值操作
    函数 功能
    set& operator=(const set &st)

    重载等号操作符

    swap(st) 交换两个集合容器
    set大小操作
     函数  功能
     size()  返回容器中元素的数目
     empty()  判断容器收为空
    set插入和删除操作
    函数 功能
    insert(elem) 在容器中插入元素。
    clear() 清除所有元素
    erase(pos) 删除pos迭代器所指的元素,返回下一个元素的迭代器
    erase(beg, end) 删除区间[beg,end)的所有元素 ,返回下一个元素的迭代器
    erase(elem) 删除容器中值为elem的元素
    set查找操作
    函数 功能
    find(key) 查找键key是否存在,若存在,返回该键的元素的迭代器;若不存在,返回set.end()
    count(key) 查找键key的元素个数
    lower_bound(keyElem) 返回最后一个key<=keyElem元素的迭代器
    upper_bound(keyElem) 返回第一个key>keyElem元素的迭代器
    equal_range(keyElem) 返回容器中key与keyElem相等的上下限的两个迭代器,这两个迭代器被放在对组(pair)中
  • 相关阅读:
    【LGOJ4147】玉蟾宫
    【BJWC2012】冻结
    【JSOI2016】最佳团体
    TCP三次握手是什么?为什么要进行三次握手?两次,四次握手可以吗?
    TCP 和 UDP的最完整的区别
    素数环问题为什么不能是奇数?
    malloc、calloc、new的区别
    请实现两个函数,分别用来序列化和反序列化二叉树
    int* &p 讲解
    c++中常用容器讲解
  • 原文地址:https://www.cnblogs.com/yongqiang/p/5746754.html
Copyright © 2020-2023  润新知