1.关于set
C++ STL 之所以得到广泛的赞誉,也被很多人使用,不只是提供了像vector, string, list等方便的容器,更重要的是STL封装了许多复杂的数据结构算法和大量常用数据结构操作。vector封装数组,list封装了链表,map和set封装了二叉树等,在封装这些数据结构的时候,STL按照程序员的使用习惯,以成员函数方式提供的常用操作,如:插入、排序、删除、查找等。让用户在STL使用过程中,并不会感到陌生。
关于set,必须说明的是set关联式容器。set作为一个容器也是用来存储同一数据类型的数据类型,并且能从一个数据集合中取出数据,在set中每个元素的值都唯一,而且系统能根据元素的值自动进行排序。应该注意的是set中数元素的值不能直接被改变。C++ STL中标准关联容器set, multiset, map, multimap内部采用的就是一种非常高效的平衡检索二叉树:红黑树,也成为RB树(Red-Black Tree)。RB树的统计性能要好于一般平衡二叉树,所以被STL选择作为了关联容器的内部结构。
2.set的定义 必须引入头文件 #include <set>
set<typename> name;
set<typename> Arrayname[100] // 这里定义了一百个set容器,下标为0~99;
3.set元素的访问
set<typename>::iterator it;
这样就得到了迭代器it,并且可以通过*it来访问set里面的元素。
除开vector和string之外的STL都不支持*(it+i)的访问方式
#include <iostream>
#include <set>
#include <string>
using namespace std;
int main() {
set<int> a;
int n;
cin>>n; // n代表要输入的数
while(n--)
{
int tmp;
cin>>tmp;
a.insert(tmp);
}
for(auto it=a.begin();it!=a.end();it++)
cout<<*it<<" ";
return 0;
}
// 输出结果:
G:\clion\qifei\cmake-build-debug\qifei.exe
6
6
5
4
7
5
4
4 5 6 7
Process finished with exit code 0
4.set常用函数的实例解析
#include <iostream>
#include <set>
#include <string>
using namespace std;
int main() {
set<int> a;
int n;
cin>>n; // n代表要输入的数
while(n--)
{
int tmp;
cin>>tmp;
a.insert(tmp);
}
set<int>::iterator it=a.find(5);
cout<<*it<<endl;
return 0;
}
// 输出结果:
G:\clion\qifei\cmake-build-debug\qifei.exe
3
1
2
5
5
Process finished with exit code 0
erase()
删除单个元素
a.erase(it),it为要删除的元素的迭代器
#include <iostream>
#include <set>
#include <string>
using namespace std;
int main() {
set<int> a;
int n;
cin>>n; // n代表要输入的数
while(n--)
{
int tmp;
cin>>tmp;
a.insert(tmp);
}
set<int>::iterator it=a.find(5);
a.erase(it);
for(it=a.begin();it!=a.end();it++)
cout<<*it<<" ";
return 0;
}
// 输出结果:
G:\clion\qifei\cmake-build-debug\qifei.exe
5
4 5 1 2 3
1 2 3 4
Process finished with exit code 0
a.erase(value),value为要删除的元素的值。
#include <iostream>
#include <set>
#include <string>
using namespace std;
int main() {
set<int> a;
int n;
cin>>n; // n代表要输入的数
while(n--)
{
int tmp;
cin>>tmp;
a.insert(tmp);
}
set<int>::iterator it;
a.erase(8);
for(it=a.begin();it!=a.end();it++)
cout<<*it<<" ";
return 0;
}
// 输出结果:
G:\clion\qifei\cmake-build-debug\qifei.exe
4
8 5 3 9
3 5 9
Process finished with exit code 0
a.erase(first,last),first为对应要删除区间的开始的迭代器,last为要删除区间的尾迭代器的下一个地址。
#include <iostream>
#include <set>
#include <string>
using namespace std;
int main() {
set<int> a;
int n;
cin>>n; // n代表要输入的数
while(n--)
{
int tmp;
cin>>tmp;
a.insert(tmp);
}
set<int>::iterator it=a.find(8);
set<int>::iterator ptr=a.find(3);
a.erase(ptr,it);
for(it=a.begin();it!=a.end();it++)
cout<<*it<<" ";
return 0;
}
// 输出结果:
G:\clion\qifei\cmake-build-debug\qifei.exe
8
1 2 4 3 8 5 6 10
1 2 8 10
Process finished with exit code 0
size()用来获得set的元素个数。
#include <iostream>
#include <set>
#include <string>
using namespace std;
int main() {
set<int> a;
int n;
cin>>n; // n代表要输入的数
while(n--)
{
int tmp;
cin>>tmp;
a.insert(tmp);
}
cout<<a.size()<<endl;
return 0;
}
// 输出结果:
G:\clion\qifei\cmake-build-debug\qifei.exe
10
1 2 3 4 5 66 7 8 9 3
9
Process finished with exit code 0
#include <iostream>
#include <set>
#include <string>
using namespace std;
int main() {
set<int> a;
int n;
cin>>n; // n代表要输入的数
while(n--)
{
int tmp;
cin>>tmp;
a.insert(tmp);
}
a.clear();
cout<<a.size()<<endl;
return 0;
}
// 输出结果:
G:\clion\qifei\cmake-build-debug\qifei.exe
10
4 5 6 12 3 789 1 2 3 4
0
Process finished with exit code 0
c++ std中set与unordered_set区别和map与unordered_map区别类似:
set基于红黑树
实现,红黑树具有自动排序
的功能,因此map内部所有的数据,在任何时候,都是有序的。unordered_set基于哈希表
,数据插入和查找的时间复杂度很低,几乎是常数时间,而代价是消耗比较多的内存,无自动排序功能
。底层实现上,使用一个下标范围比较大的数组来存储元素,形成很多的桶,利用hash函数对key进行映射到不同区域进行保存。
#include <iostream>
#include <unordered_set>
#include <string>
using namespace std;
int main() {
unordered_set<int> a;
int n;
cin>>n; // n代表要输入的数
while(n--)
{
int tmp;
cin>>tmp;
a.insert(tmp);
}
for(auto it=a.begin();it!=a.end();it++)
cout<<*it<<" ";
return 0;
}
// 输出结果:
G:\clion\qifei\cmake-build-debug\qifei.exe
8
1 2 36 4 5 1 2 10
10 5 1 36 2 4 // (顺序依赖于 hash function)
Process finished with exit code 0
原文:https://www.cnblogs.com/Yqifei/p/12660154.html