STL还用不熟(爆哭)所以就有了这个合集
随做题补充…没用到的情况下实在不好吸收消化
①vector (向量)
#include<vector> //需要头文件
//以下为初始化
vector<int>a // 定义了一个int类型的向量
vector<int>a (b) // //此处b也为向量,用b向量来创建a向量,整体复制性赋值
vector<int>a (b.begin(),b.begin()+3); //定义a向量为b中第0个到第2个(共3个)元素
// 向量a也可以从数组中获取初值
int c[7]={1,2,3,4,5,9,8};
vector<int> a(c,c+7); // 将数组中下标为0到6的数据都作为a向量的初值
可以将vector理解为一个更加方便的数组
常用命令:
a.push_back(5); 在a的最后一个向量后插入一个元素,其值为5
a.back(); 返回a的最后一个元素
a.front(); 返回a的第一个元素
a[i]; 与数组的使用无异,返回a的第i个元素,当且仅当a[i]存在
a.clear(); 清空a中的元素
a.empty(); 判断a是否为空,空则返回ture,不空则返回false
a.pop_back(); 删除a向量的最后一个元素
a.size(); 返回a中元素的个数;
a.capacity(); 返回a在内存中总共可以容纳的元素个数
一些可能会有奇效的命令【区间前闭后开的情况很常见,需要注意】:
a.swap(b); b为向量,将a中的元素和b中的元素进行整体性交换
a==b; b为向量,向量的比较操作还有!=,>=,<=,>,<
a.erase(a.begin()+1,a.begin()+3); 删除a中第1个(初始从第0个算起)到第2个元素,也就是说删除的元素是从a.begin()+1到a.begin()+3【区间前闭后开,和sort()类似】
a.insert(a.begin()+1,5); 在a的第1个元素(初始从第0个算起)的位置插入数值5,如a为1,2,3,4,插入元素后为1,5,2,3,4
a.insert(a.begin()+1,3,5); 在a的第1个元素(初始从第0个算起)的位置插入3个数,其值都为5
a.insert(a.begin()+1,c+3,c+6); c为数组,在a的第1个元素(初始从第0个算起)的位置插入c的第3个元素到第5个元素(不包括c+6)
a.assign(b.begin(), b.begin()+3) b为向量,将b中下标为0到2的向量赋给a【又是前闭后开】
a.assign(4,2) 是a只含4个元素,且每个元素为2
a.resize(10) 将a的现有元素个数调至10个,多则删,少则补,其值随机
a.resize(10,2) 将a的现有元素个数调至10个,多则删,少则补,其值为2
a.reserve(100) 将a的容量(capacity)扩充至100,也就是说现在测试a.capacity();的时候返回值是100
这种操作只有在需要给a添加大量数据的时候才显得有意义,因为这将避免内存多次容量扩充操作(当a的容量不足时电脑会自动扩容,当然这必然降低性能)
②queue (队列)
#include<queue> //需要头文件
//以下为初始化
queue<int>q; //定义一个int类型的队列
队列是一个前出后进的结构
常用命令:
q.push(x); 将x接到队列的末端。
q.pop(); 弹出队列的第一个元素,注意,并不会返回被弹出元素的值。
q.front(); 返回最早被压入队列的元素。
q.back(); 返回最后被压入队列的元素。
q.empty(); 当队列空时,返回true,否则返回false
q.size(); 返回队列中元素个数
priority_queue(优先队列)
可以用来实现堆,优先级越高的元素越先出队
#include<queue> //需要头文件
//以下为初始化
priority_queue<Type,Container,Functional>pq; //定义格式
priority_queue<Type>pq //使用基本数据类型时
//常用命令与队列基本相同,多了一个很重要的命令:
pq.top(); 访问堆顶元素
另外pq.front(),pq.back()在优先队列里不存在!
Type为数据类型;Container为容器类型(必须是用数组实现的,如vector,deque等,不可用list);Functional为优先级比较方式
当需要用自定义的数据时才需要传入所有三个参数,使用基本数据类型时,只要传入数据即可,默认是大根堆
priority_queue<Type,vector<Type>,less<Type> >pq; //大根堆
priority_queue<Type,vector<Type>,greater<Type> >pq; //小根堆
③stack (栈)
#include<stack> //需要头文件
stack<int>s; //定义一个int类型的栈
栈是一个先进后出,后进先出的结构
常用命令:
s.push(x); 将x压入栈中,叠罗汉形式
s.pop(); 删除栈顶部的元素,注意,并不会返回该元素的值
s.top(); 返回栈顶部元素的值
s.size(); 返回栈中元素的个数
s.empty(); 检查栈是否为空,是返回True,否则返回False
④pair (对组)
#include<utility> //所需头文件
pair<int,double>p; //创建pair对象时必须提供两个变量名,它们不必相同
typedef pair<数据类型1,数据类型2> p; //这样定义pair更方便(如配合队列一起使用的时候,让一个点的坐标入队)
pair的实现是结构体,故可以直接访问它的成员变量
将两个数据组合成一个数据,整体可以作为函数的返回值,并且可以用first和end两个成员变量来访问这两个数据的值
pair<T1, T2> p1; 创建一个空的pair对象(使用默认构造),它的两个元素分别是T1和T2类型,采用值初始化。
pair<T1, T2> p1(v1, v2); 创建一个pair对象,它的两个元素分别是T1和T2类型,其中first成员初始化为v1,second成员初始化为v2。
make_pair(v1, v2); 以v1和v2的值创建一个新的pair对象,其元素类型分别是v1和v2的类型。
p1 < p2; 两个pair对象间的小于运算,遵循字典序顺序:从v1开始比较,若v1.first==v2.first才会用各自的second继续比较
p1 == p2; 如果两个对象的first和second依次相等,则这两个对象相等;该运算使用元素的==操作符。
p1.first; 返回对象p1中名为first的公有数据成员
p1.second; 返回对象p1中名为second的公有数据成员
⑤ sort(STL里自带的稳定O(nlogn)排序)
#include<algorithm> //所需头文件
sort(a.begin(),a.end(),cmp)
第一个参数为待排序的数组的起始地址
第二个参数为待排序数组的终止位置的下一位,因为sort()所处理的数组范围是前闭后开的区间,不写下一位的话是不会处理到你想要的终止位置的
第三个参数为排序方法,可不填,默认为升序排序,可根据自己的需求定义cmp函数
bool cmp(int a,int b)
{
return a>b; //降序
//升序为a<b
}
⑥map(能建立一一对应关系的容器,可以认为是STL提供给我们的哈希表)
#include<map> //所需头文件
map<int,string>m; //例:定义一个key(关键字)为int,value为string类型的map容器,索引为int类型,索引对应的内容为string类型
插入数据(3种方式):
map<int,string>s;
s.insert(pair<int,string>(1,"student01")) // 方法1
s.insert(map<int, string>::value_type(1,"student01")); //方法2
s[1]="student01"; //方法3
值得注意的是: 方法1和方法2遵循集合的唯一性,即若当前key(即1)已经对应了一个value值,那么再用方法1和方法2试图插入该key和其他value值的对应关系是无效的,但用方法3可以直接修改key和value的对应关系。
另外,map容器在插入数据时是保持有序的,按key值进行升序排序(字符则以ASCII码对应的数字来升序排序)
#include<bits/stdc++.h>
using namespace std;
map<int,string>s;
int main()
{
s[0]="student00";
s[1]="student01";
s[2]="student02";
//反向遍历
for (map<int,string>::reverse_iterator it=s.rbegin();it!=s.rend();it++)
cout<<it->first<<" "<<it->second<<endl;
cout<<endl;
//正向遍历(把反向遍历里的reverse_iterator改成iterator,rbegin,rend改为begin,end也可)
for (int i=0;i<s.size();i++)
cout<<i<<" "<<s[i]<<endl;
//map的大小
cout<<s.size()<<endl;
//查找并获取map中元素(判定其是否存在)
cout<<s.count(1)<<endl; //方法1:count,存在则count返回值为1,否则为0(出现次数)
//方法2:find,通过迭代器iterator来寻找并定位某个key-value对应关系
map<int,string>::iterator it; //it本质上为指向pair类型的指针
it=s.find(0); //目标存在,it->first返回该key值,it->second返回value值
cout<<it->first<<" "<<it->second<<endl;
it=s.find(99); //目标不存在,it返回值同end()
cout<<it->first<<" "<<it->second<<endl;
return 0;
}
https://www.cnblogs.com/fnlingnzb-learner/p/5833051.html 这篇博客讲解map很详细
⑦set(集合)
#include<set> //所需头文件
set<int>s; //建立一个元素均为int类型的集合
set就是数学意义上的集合,其中的元素具有唯一性
s.begin() 返回指向第一个元素的迭代器
s.clear() 清除所有元素
s.count() 【极常用】返回某个值元素的个数(由于集合元素的唯一性,返回值只可能为0或1) //常用于判重
s.empty() 如果集合为空,返回true
s.end() 返回指向最后一个元素之后的迭代器,不是最后一个元素
s.erase() 删除集合中的元素
s.find() 返回一个指向被查找到元素的迭代器
s.insert() 【极常用】在集合中插入元素
s.max_size() 返回集合能容纳的元素的最大限值
s.size() 集合中元素的数目
s.swap() 交换两个集合变量