STL-queue-vector-map-set

五、STL

5.1优先队列

普通的队列是一种先进先出的数据结构,元素在队列尾追加,而从队列头删除。

在优先队列中,元素被赋予优先级。当访问元素时,具有最高优先级的元素最先删除。优先队列具有最高级先出 (first in, largest out)的行为特征。

首先要包含头文件#include<queue>, 他和queue不同的就在于我们可以自定义其中数据的优先级, 让优先级高的排在队列前面,优先出队。

优先队列具有队列的所有特性,包括队列的基本操作,只是在这基础上添加了内部的一个排序,它本质是一个堆实现的。

和队列基本操作相同:

  • top 访问队头元素
  • empty 队列是否为空
  • size 返回队列内元素个数
  • push 插入元素到队尾 (并排序)
  • emplace 原地构造一个元素并插入队列
  • pop 弹出队头元素
  • swap 交换内容

prioriy_queue<Type,Container,Functional>
Type 就是数据类型,Container 就是容器类型(Container必须是用数组实现的容器,比如vector,deque等等,但不能用 list。STL里面默认用的是vector),Functional 就是比较的方式。

一般需要用自定义的数据类型或者比较方式的时候才传入三个参数,使用基本数据类型时,只需要传入数据类型,默认是大顶堆

升序,小顶堆
priority_queue<int,vector<int>,greater<int> >

降序,大顶堆
priority_queue<int,vector<int>,less<int> >

注意 最后‘>’前面有一个空格

5.1.1 基本优先队列
#include<queue>
#include<iostream>
using namespace std;
int main()
{
	//基础类型,默认是大顶堆(降序)
	priority_queue<int> a;
	priority_queue<string> b;
	//小顶堆(降序)
	priority_queue<int,vector<int>,greater<int> > c;

	//入队
	for(int i=0;i<5;i++)
	{
		a.push(i);c.push(i);
	}
	b.push("abc");
	b.push("cab");
	b.push("abcd");
	//出队
	while(!a.empty())
	{
		cout<<a.top();
		a.pop();
	}
	while(!c.empty())
	{
		cout<<c.top();
		c.pop();
	}
	while(!b.empty())
	{
		cout<<b.top();
		b.pop();
	}
}

运行结果:
43210
01234
cab abcd abc

5.1.2 用pair做优先队列元素

规则:pair的比较,先比较第一个元素,第一个相等比较第二个。
pair是数据类型,不需要再传入Container和Functional,默认是大顶堆,最大的元素优先级最高,先出队

#include <iostream>
#include <queue>
#include <vector>
using namespace std;
int main()
{
    priority_queue<pair<int, int> > a;
    pair<int, int> b(1, 2);
    pair<int, int> c(1, 3);
    pair<int, int> d(2, 5);
    a.push(d);
    a.push(c);
    a.push(b);
    while (!a.empty())
    {
        cout << a.top().first << ' ' << a.top().second << '\n';
        a.pop();
    }
}

5.2 vector、map、set

#include<iostream>  //C++标准输入输出,cin/cout
#include<cstdlib>
#include<cstdio>    //c标准输入输出,scanf/printf
#include<algorithm> //常用算法,比如快速排序sort函数
#include<map><vector><string><set> //STL相应模块
#include<cstring>    //c语言字符串相关,memset函数所在头文件

map和set都支持的操作有:

count()
insert()//这个vector也支持
find()
erase()

一、vector用法

2.1 vector长度

	v.capacity();//容器目前能存储的元素个数
	v.size();//当前容器存储的元素个数
	v.reverse();//表示预留存储空间但不创建对象,需要用insert或者push_back创建对象
	v.resize();//既分配了空间也创建了对象,空间就是capacity,对象就是元素

区别
reverse()只修改capacity大小,不修改size大小
resize()既修改capacity大小,也修改size大小

analogy:
建造一幢房子,这个房子的空间可以容纳50个人,但只是说有这个空间容纳的下,不代表已经有了50个人,这是capacity,当有50个人进入房子的时候,这才是size
reverse想重建这个房子,使房子能装下80人,如果这个房子原来是空的,那么扩建后就还是空的,如果房子里原来有50人,那么扩建后就还有50人(意味着还能再进入30人就满了)
resize是重建这个房子同时把房子填满,如果房子里原来的人比房子的容量小,那么指定一些人进入房子,如果原来的人比房子容量大,就把一些人赶出去。

2.2vector初始化

1.不带参数结构

vector<int> a;

2.带参数结构

(1).初始化vector的大小,但每个元素为默认值0
	vector<int> a(10)
(2).初始化大小同时指定初始值
	vector<int> a(10,1)  //vector被初始化为10个1

3.通过数组地址初始化

	int a[5]={1,2,3,4,5};
	vector<int> b(a,a+5//注意b是用a+5,因为地址是从0到5(左闭右开)

4.通过同类型的vector初始哈

	vector<int> a(5,1)//初始化a为5个1
	vector<int> b(a)//用a初始化b

5.通过insert初始化

(1) //将同类型的迭代器对应的始末区间(左闭右开)内的值插入到vector中
	vector<int> a(6,1);
	vector<int> b;
	b.insert(b.begin(),a.begin(),a.begin()+3);
	//将a[0]~a[2]插入到b的开始处
	
(2)//数组地址空间实现插入
	int a[6]={1,1,1,1,1,1};
	vector<int> b;
	b.insert(b.begin(),a,a+6);
	
(3)//插入m个值为n的元素
	b.insert(b.begin(),m,n);

6.通过copy函数赋值

	vector<int> a(5,1);
	int a1[5]={2,2,2,2,2};
	vector<int> b(10);
	
	copy(a.begin(),a.end(),b.begin());
	//将a中全部元素拷贝到b开始位置
	
	copy(a1,a1+5,b.begin()+5)
	//将a1中元素拷贝到b中5~9的位置

2.3 常见的操作

1.insert
(1)插入一个元素
v.insert(位置,元素)
eg:v.insert(v.begin(),e)//用迭代器表示位置
//注意左闭右开区间,如果l=v.size()
//那么v的区间是:v.begin()~v.begin()+l

(2)插入多个元素
v.insert(位置,n,e)//插入n个相同元素e
eg:v.insert(v.begin()+1,2,3)
//在v[1]前面插入2个3

v.insert(位置,beg,end)//插入[beg,end)区间的元素
eg:v.insert(v.begin(),v1.begin(),v1.end())//在v开始处插入v1
2.vector pile[maxn]

定义了maxn个vector:
pile[i] (i=0~maxn-1),每个pile[i]是一个可增长的数组(vector)

3.使用模板注意

模板使用的时候不可以用下标只能用迭代器

1.sort
错误:sort(v,v+n)
正确:sort(v.begin(),v.end())
2.
lower_bound(v.begin(),v.end(),x)
upper_bound(v.begin(),v.end(),x)
3.
find(a.begin(),a.end(),10);
//在a中找10

4.back和front
v.back()//返回v的最后一个元素
v.front()//返回v的第一个元素
还可以用back和front给第一个、最后一个元素赋值
5.删除和添加

1.添加

	v.push_back(e);//向v的结尾处加入e

2.删除

(1)删除最后一个
	v.pop_back();
(2)删除指定位置
	v.erase(v.begin(),v.begin()+3);
	//删除了v[0].v[1].v[2]
(3)清空v
	v.clear();
6.其他
  1. empty()
    return 0不为空
    return 1为空

2.4 遍历

数组下标
for(int i=0;i<v.size();i++)
{
	cout<<v[i]<<endl;
}
迭代器
for (vecotr<int>::iterator iter=v.begin();iter!=v.end();iter++)
{
	std::cout<<*iter<<endl;
}
C++11 aotu
for(auto i:v)
{
	cout<<v[i]<<endl;
}

三、map的用法

map<key_type,value_type> name;
在map总,元素是按照key值进行排序的

1.插入
	map<char,int> ctoi;
1.ctoi.insert(pair<char,int>("Monday",1));

2.ctoi.insert(make_pair("Monday",1));

3.ctoi.insert({"Monday",1});

4.ctoi["Monday"]=1;
2.count
ctoi.count("某个key值");
//map中存在return 1;否则return 0
3.迭代器遍历
	map<char,int>::iterator item=ctoi.begin();
	while(item!=ctoi.end())
	{
		用item->first取key值
		item->second取value值
	}
4.查找
	map<char,int>::iterator iter;
	if((iter=ctoi.find("要查找的元素"))!=ctoi.end())
5.删除

erase可以删除指定key值的元素

ctoi.erase("name")

四、set用法

set内部元素在自动排序且去重


count()        用来查找set中某个某个键值出现的次数因为一个键值在set只可能出现0或1次,这样就变成了判断某一键值是否在set出现过了。


erase(iterator)    删除定位器iterator指向的值

erase(first,second)   删除定位器first和second之间的值

erase(key_value)   删除键值key_value的值


find()         返回给定值的定位器,如果没找到则返回end()。


1.遍历
	set<int> testset;

通常使用迭代器
for(set<int>::iterator it=testset.begin();it!=testset.end();++it)
	cout<<*it<<endl;

*这种只有在C++11编译器下可以通过
for(auto i:testset)
	cout<<i<<endl;
2.insert
	set<int> testset;
	
testset.insert(元素);
testset.insert(a,a+5);
testset.insert(v.begin(),v.end());

3.初始化
1 用数组初始化

	int a[5]={1,2,3,4,5};
	set<int> s(a,a+5);
	
2 用另一个set初始化

	set<int> a;
	set<int> testset(a);
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值