STL--set容器

目录

一、set容器基本概念

二、set构造和赋值

 三、set 大小和交换

 四、set 插入和删除

 五、set 查找和统计

 六、set 和 multiset 的区别

 七、set 容器排序

 八、set 容器自定义类型数据排序


一、set容器基本概念

1. 功能:所有元素都会在插入时自动排好序

2. 本质:set/multiset 属于关联式容器,底层结构是用二叉树实现的

3. set和multiset的区别

        set 不允许容器中有重复的元素

        multiset 允许容器中有重复的元素

二、set构造和赋值

构造:

  • set<T>  st;                          // 默认构造函数
  • set(const  set  &  st);          // 拷贝构造函数

赋值:

  • set  & opeartor=(const  set  &  st);         // 重载等号操作符
	#include<iostream>
	using namespace std;
	#include<set>
	
	// 遍历
	void print_set(set<int> &S)
	{
		for(set<int>::iterator it=S.begin();it!=S.end();it++)
		{
			cout<<*it<<"  ";
		}
		cout<<endl;
	}
	
	// set 容器构造和赋值
	int main()
	{
		set<int> s1;
	
		// 插入数据  只有insert的方法
		for(int i=0;i<10;i++)
		{
			s1.insert(i);
		}
		for(int i=0;i<10;i++)
		{
			s1.insert(i);
		}
		// 插入多个数据只存储一个
		// set 容器在所有元素插入的时候会自动排序
		// set  容器不允许插入重复的值
		print_set(s1);
	
		// 拷贝构造
		set<int> s2(s1);
		print_set(s2);
	
		// 赋值
		set<int> s3;
		s3 = s1;
		print_set(s3);
		return 0;
	}

 三、set 大小和交换

set容器不允许重新指定大小,因为会用相同的容器填充,而set容器不允许有相同的数据

  • size();                     // 返回容器中元素的个数
  • empty();                 // 判断容器是否为空
  • swap();                  // 交换两个集合容器
	#include<iostream>
	using namespace std;
	#include<set>
	
	// 遍历
	void print_set(set<int> &S)
	{
		for(set<int>::iterator it=S.begin();it!=S.end();it++)
		{
			cout<<*it<<"  ";
		}
		cout<<endl;
	}
	// set 容器大小和交换
	int main()
	{
		set<int> s1;
	
		// 插入数据  只有insert的方法
		for(int i=0;i<10;i++)
		{
			s1.insert(i);
		}
	
		print_set(s1);
		if(s1.empty())
		cout<<"s1为空"<<endl;
		else
		cout<<"s1不为空"<<endl;
	
		// 大小
		cout<<"s1的大小为:"<<s1.size()<<endl;
	
		set<int> s2;
		s2.insert(100);
		s2.insert(200);
		s2.insert(300);
		s2.insert(400);
	
	
		cout<<"交换前:"<<endl;
		print_set(s1);
		print_set(s2);
		// 交换
		s1.swap(s2);
		cout<<"交换后:"<<endl;
		print_set(s1);
		print_set(s2);
		return 0;
	}

 四、set 插入和删除

  • insert(elem);                           // 在容器中插入元素

  • erase(pos);                            // 删除pos迭代器所指向的元素,返回下一个元素的迭代器
  • erase(beg,  end);                  // 删除(beg,end)区间内的所有元素,返回下一个元素的迭代器
  • erase(elem);                         // 删除容器中值为elem的元素

  • clear();                                 //清空容器中所有数据
	#include<iostream>
	using namespace std;
	#include<set>
	
	// 遍历
	void print_set(set<int> &S)
	{
		for(set<int>::iterator it=S.begin();it!=S.end();it++)
		{
			cout<<*it<<"  ";
		}
		cout<<endl;
	}
	// set 容器插入和删除
	int main()
	{
		set<int> s1;
	
		// 插入数据  只有insert的方法
		for(int i=0;i<10;i++)
		{
			s1.insert(i);
		}
		print_set(s1);
	
		// 删除
		cout<<"删除指定迭代器的数据\t";
		s1.erase(s1.begin());
		print_set(s1);
		// 删除的重载版本
		// 可以直接指定要删除的内容
		cout<<"删除指定的数据\t";
		s1.erase(5);
		print_set(s1);
	
		// 清空的操作
		cout<<"删除区间内所有的元素\t";
	    s1.erase(s1.begin(),s1.end());
	    print_set(s1);
	
	    // clear 清空
	    s1.clear();
	    print_set(s1);
		return 0;
	}

 五、set 查找和统计

  • find(key);                     // 查找key是否存在,若存在返回该元素的迭代器,若不存在,返回set.end();
  • count(key);                  // 统计key的元素个数
	#include<iostream>
	using namespace std;
	#include<set>
	
	// 遍历
	void print_set(set<int> &S)
	{
		for(set<int>::iterator it=S.begin();it!=S.end();it++)
		{
			cout<<*it<<"  ";
		}
		cout<<endl;
	}
	// set 容器查找和统计
	int main()
	{
		set<int> s1;
	
		// 插入数据  只有insert的方法
		for(int i=0;i<10;i++)
		{
			s1.insert(i);
		}
		print_set(s1);
	
	    set<int>::iterator pos = s1.find(100); // 返回的是迭代器的位置,没有找到返回s.end();
		if(pos!=s1.end())
		cout<<"找到你要的数的位置:"<<*pos<<endl;
		else
		cout<<"未找到你要的数"<<endl;
	
		// 统计
		int num = s1.count(2);
		cout<<"个数为:"<<num<<endl; // 只能返回0或1,set不会重复插入数据
		return 0;
	}

 六、set 和 multiset 的区别

  • set 不可以插入重复的数据,而 multiset 可以
  • set 插入数据的同时会返回插入的结果,表示插入是否成功
  • multiset 不会检测数据,因此可以插入重复数据
	#include<iostream>
	using namespace std;
	#include<set>
	
	// 遍历
	void print_set(set<int> &S)
	{
		for(set<int>::iterator it=S.begin();it!=S.end();it++)
		{
			cout<<*it<<"  ";
		}
		cout<<endl;
	}
	void print_multiset(multiset<int> &S)
	{
		for(multiset<int>::iterator it=S.begin();it!=S.end();it++)
		{
			cout<<*it<<"  ";
		}
		cout<<endl;
	}
	// set set 和 multiset 的区别
	int main()
	{
		set<int> s1;
		// 插入数据  只有insert的方法
		for(int i=0;i<10;i++)
		{
			s1.insert(i);
		}
		print_set(s1);
	
		// 利用对组,判断是否插入成功
		pair<set<int>::iterator,bool> ret = s1.insert(0); // 不能再插入0
		if(ret.second)
		cout<<"插入成功 "<<endl;
		else
		cout<<"插入失败"<<endl;
	
	    multiset<int> s2;
	    s2.insert(20);
	    s2.insert(20);
	    s2.insert(20);
	    s2.insert(300);
	    s2.insert(400);
	    print_multiset(s2);
		return 0;
	}

 七、set 容器排序

利用仿函数,可以改变排序规则

	#include<iostream>
	using namespace std;
	#include<set>
	
	// 在类内写的仿函数
	class my_compare
	{
	public:
		bool operator()(int v1,int v2)        // 重载的()
		{
			return v1>v2;
		}
	};
	// 默认的遍历方式
	void print_set(set<int> &S)
	{
		for(set<int>::iterator it=S.begin();it!=S.end();it++)
		{
			cout<<*it<<"  ";
		}
		cout<<endl;
	}
	// 遍历
	void print_set(set<int,my_compare> &S)
	{
		for(set<int,my_compare>::iterator it=S.begin();it!=S.end();it++)
		{
			cout<<*it<<"  ";
		}
		cout<<endl;
	}
	// set 容器排序
	int main()
	{
		set<int>  s;
		s.insert(10);
		s.insert(40);
		s.insert(67);
		s.insert(23);
		s.insert(89);
		print_set(s);
	
		// 要在还没有插入数据的时候就设定排序规则
		set<int,my_compare> s1;
		s1.insert(10);
		s1.insert(40);
		s1.insert(67);
		s1.insert(23);
		s1.insert(89);
		
		print_set(s1);
	
		// 默认排序规则为从小打到大的升序
		// 改变排序的规则为从大到小的降序
		return 0;
	}

 八、set 容器自定义类型数据排序

	#include<iostream>
	using namespace std;
	#include<set>
	
	// 自定义数据
	class person
	{
	public:
		person(string name,int age)
		{
			this->name=name;
			this->age=age;
		}
		string name;
		int age;
	};
	
	// 仿函数
	class my_compare
	{
	public:
		bool operator()(const person &p1,const person &p2)
		{
			// 按照年龄的  降序排列
			return p1.age>p2.age;
		}
	};
	// set 容器排自定义数据序
	int main()
	{
		// 创建person对象
		person p1("TOM",20);
		person p2("JERRY",30);
		person p3("mike",23);
		person p4("good",45);
	
	
		set<person,my_compare> s1;
	
		// 对于自定义的数据类型,要指定排序规则
		s1.insert(p1);
		s1.insert(p2);
		s1.insert(p3);
		s1.insert(p4);
	
		for(set<person>::iterator it=s1.begin();it!=s1.end();it++)
		{
			cout<<"姓名:"<<it->name<<"\t年龄:"<<it->age<<endl;
		}
		return 0;
	}

  • 2
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值