> 文章列表 > set/multiset容器

set/multiset容器

set/multiset容器

1、set/multiset容器简介

set/multiset容器
但是 set 容器只有键值,在插入数据的时候会自动根据 键值 进行排序,所以不允许有相同的键值存在,也不能修改 set 容器元素值,会破坏 set 的数据结构。set 容器的迭代器是只读迭代器
set/multiset容器

2、set容器 API 操作

set/multiset容器
set/multiset容器

3、set 容器的使用

set容器中只能使用 insert 一个一个插入数据

void printSetInt(set<int> &s)
{set<int>::iterator it;for(it=s.begin(); it!=s.end();it++){cout<<*it<<" ";}cout<<endl;
}void printSetInt(set<int,MyCompare> &s)
{set<int,MyCompare>::iterator it;for(it=s.begin(); it!=s.end();it++){cout<<*it<<" ";}cout<<endl;
}void test01()
{set<int,MyCompare> s1;           //使用仿函数更改排序规则  s1.insert(30);                   //set容器只能使用 insert 一个一个插入数据,,因为要根据插入的数据进行排序,也没有 n个元素的拷贝构造,因为set中要求键值是不能重复的 s1.insert(10);s1.insert(20);s1.insert(20);s1.insert(40);printSetInt(s1);
}

set/multiset容器

4、更改 set 容器的排序规则(定义 set 容器时修改)

set/multiset容器
但是 set 函数的排序规则默认是按照从小到大,所以使用仿函数更改排序规则从 大到小

#include <iostream>
#include<set>
using namespace std;
//仿函数实质上是一个类,使用仿函数更改排序规则
class MyCompare
{
public:bool operator()(int v1, int v2){return v1>v2;}
};
void printSetInt(set<int> &s)
{set<int>::iterator it;for(it=s.begin(); it!=s.end();it++){cout<<*it<<" ";}cout<<endl;
}void printSetInt(set<int,MyCompare> &s)
{set<int,MyCompare>::iterator it;for(it=s.begin(); it!=s.end();it++){cout<<*it<<" ";}cout<<endl;
}void test01()
{set<int,MyCompare> s1;           //使用仿函数更改排序规则  s1.insert(30);                   //set容器只能使用 insert 一个一个插入数据,,因为要根据插入的数据进行排序,也没有 n个元素的拷贝构造,因为set中要求键值是不能重复的 s1.insert(10);s1.insert(20);s1.insert(20);s1.insert(40);printSetInt(s1);
}

set/multiset容器

5、如果 set 容器存放的是自定义类型,则需要更改排序规则

#include <iostream>
#include<set>
using namespace std;class Person
{friend class MyComparePerson;   //访问私有属性的仿函数作为该类的友元 friend ostream& operator<<(ostream &out, Person ob);   //类外函数访问私有属性作为该类的友元 
private:int num;string name;float score;
public:Person(){}Person(int num,string name, float score){this->num = num;this->name = name;this->score = score;}
};//cout<<(*it);    重载 cout<<(*it);    中的输出运算符 
ostream& operator<<(ostream &out, Person ob)
{out<<ob.num<<" "<<ob.name<<" "<<ob.score<<endl;return out;
}class MyComparePerson      //仿函数更改排序规则 
{
public:bool operator()(Person ob1, Person ob2)    //仿函数更改排序规则 {return ob1.num < ob2.num;}
};
void printSetInt(set<Person,MyComparePerson>  &s)
{set<Person,MyComparePerson> ::iterator it;for(it=s.begin(); it!=s.end();it++){cout<<(*it);                        //cout的是每一个对象,所以可以为 (*it).num<<(*it).name<<(*it).score,并且要将 void printSetInt(set<Person,MyComparePerson>  &s)设置为友元函数,但是这个涉及到函数关系,也不好设置,所以可以使用上面的重载输出运算符 }                                       //所以可以使用上面的重载输出运算符 cout<<endl;              
}
void test02()
{set<Person,MyComparePerson>  s1;s1.insert(Person(100,"lucy", 88.8f));s1.insert(Person(104,"bob", 99.8f));s1.insert(Person(103,"tom", 77.8f));s1.insert(Person(101,"德玛", 66.8f));s1.insert(Person(105,"寒冰", 55.8f));printSetInt(s1);
}
int main(int argc, char *argv[])
{test02();return 0;
}

set/multiset容器
对于cout的是每一个 person对象,所以可以为 (*it).num<<(*it).name<<(*it).score,并且要将 void printSetInt(set<Person,MyComparePerson> &s)设置为友元函数,但是这个涉及到函数的位置关系,也不好设置,所以最简单的是使用上面的重载输出运算符,将ostream& operator<<(ostream &out, Person ob)设置 person 类的 友元函数

6、set的find 和 count 函数

find 从前往后查找 键值,直到 容器末尾
count(key);//查找键key的元素个数 set容器的结果只能是0或1,因为键值是不可重复的

void test03()
{set<int> s1;s1.insert(10);s1.insert(30);s1.insert(50);s1.insert(70);s1.insert(90);printSetInt(s1);set<int>::const_iterator ret;    // find的返回值是一个迭代器,所以要申明这个容器的迭代器 ret = s1.find(50);if(ret != s1.end()){cout<<"找到的结果:"<<*ret<<endl;}//count(key);//查找键key的元素个数  set容器的结果只能是0或1cout<<s1.count(50)<<endl;
}int main(int argc, char *argv[])
{test02();return 0;
}

set/multiset容器

7、set 的lower_bound、upper_bound、equal_range函数

equal_range函数可以同时 返回两个迭代器,兼具 lower_bound、upper_bound的功能
equal_range(keyElem);//返回容器中key与keyElem相等的上下限的两个迭代器
返回值类型为pair 对组
set/multiset容器

#include <iostream>
#include<set>
using namespace std;void test04()
{set<int> s1;s1.insert(10);s1.insert(30);s1.insert(50);s1.insert(70);s1.insert(90);printSetInt(s1);set<int>::const_iterator ret;//lower_bound(keyElem);//返回第一个key>=keyElem元素的迭代器。(下限)ret = s1.lower_bound(50);if(ret !=s1.end()){cout<<"下限为:"<<*ret<<endl;}//upper_bound(keyElem);//返回第一个key>keyElem元素的迭代器(上限)ret = s1.upper_bound(50);if(ret !=s1.end()){cout<<"上限为:"<<*ret<<endl;}//equal_range(keyElem);//返回容器中key与keyElem相等的上下限的两个迭代器//返回值类型为pair 对组pair< set<int>::const_iterator, set<int>::const_iterator> p;p = s1.equal_range(50);if(p.first  != s1.end())    //左值{cout<<"下限为:"<<*(p.first)<<endl;}if(p.second != s1.end())    //右值{cout<<"上限为:"<<*(p.second)<<endl;}
}int main(int argc, char *argv[])
{test04();return 0;
}

set/multiset容器

7、注意事项

set和multiset 的头文件都是 set
set的键值是不可重复的,multiset 的键值是可重复的
其他都是一样的

看历史网