助力PAT甲级/乙级取得满分的小技巧,STL容器

STL容器的高级玩法

写在前面:本人于2020PAT甲级取得满分(见本人其他博客),在刷题过程中我有了很多自己的小经验和技巧,在这里分享给大家,祝大家刷题顺利,早日拿到免费的PAT徽章~~

注意:这里是分享小技巧,并不是全面介绍容器,此处默认你已经掌握了容器的基本用法!

1. Vector

大名鼎鼎的Vector,动态数组嘛,用起来很方便,但是你可知道vector不仅仅是动态数组,它还可以是队列/优先队列,栈?

Vector变成队列和栈的关键函数

  • erase
    你会不会感到很疑惑?删除函数有什么了不起的?竟然还能玩出花样?
    君莫急,且看:
vector<int>V;
V.push_back(1);
V.push_back(2);
V.push_back(3);
V.push_back(4);

对于栈很简单,使用:

V.erase(--V.end());
V.erase(V.rbegin());//与上面等价!
V.pop_back();

这就完成了删除最后一个元素操作!
立即推,vector等于stack,所以完全没必要去熟悉stack容器!

  • erase变队列
V.erase(V.begin());

这样就实现了删除第一个元素,这就是vector版的队列!!
至于优先队列(自定义排序顺序),可以在所有元素进入vector以后使用sort函数自定义cmp,然后实现优先队列(效率相同!!)

sort(V.begin(),V.end(),cmp);
//cmp为自定义比较关系
+
  • Vector变双端队列
V.insert(V.begin,1);

这样就在最前面插入了元素1,通过以上操作

vector在保持动态数组的同时 还是队列,双端队列,栈,优先队列!

除此之外,还有冷门Vector用法!!!!!

1.更方便的判等!

vector<int.>V1,V2;
if(V1==V2) printf(“Yes”);
else printf(“No”);

两个Vector之间可以直接用==进行判等,只有存储的元素完全相同的时候才会true

2.更方便的判断元素大小

if(V1<V2)printf("Yes");

如:

V1:1 2 2 4
V2:1 2 3 1

那么V1<V2就是true

作用:在题目要求出现不唯一的答案时,按小序列输出,通过利用sort函数可以对vector大小可以排序,然后输出第一个即可!

2.map的高级玩法**

  • 用来对数字进行排序,效率无敌快!
    比如:
int val;
map<int,int>Ma;
for(int i=0;i<N;i++
{
	scanf("%d",&val);
	Ma[val]++;
}
//这样得到的map就是有序系列,可以直接输出!!
for(auto it=Ma.begin();it!=Ma.end();it+){
	for(int j=0;j<it->second;j++){
		printf(" %d",it->first);
	}
}

强不强!!这样排序的效率远超过了set/underorder_set!!!
利用second值也可以避免重复!!!
一举两得,非常棒!!!

  • Map用来哈希映射字符串
map<string,int>Ma;
map<int,string>Mb;
string s;
int index =1;
for(int i=0;i<N;i++){
	cin>>s;
	if(Ma[s]!=0)continue;//0不存数据,下标从1开始,已经映射过的就跳过,不再映射。
	Ma[s]=index;
	Mb[index]=s;
	index++;
}

这样就把string变成了int,访问直存直取,效率无敌!!!

3.字符串string的玩法~

1.find函数

find既可以找单个字符,也可以找 字符串
如:

在这里插入图片描述除此之外,还有另外的几个find函数:
在这里插入图片描述

看名字就能懂他们的作用

rfind是find的逆序,find是从前往后,rfind就是从后往前找

string最优秀的是操作方便,可以直接用+进行连接,在很多题目中用起来简直舒服到爆,比如2018年真题中的运算树,递归遍历,string控制输出格式太好用了。
再比如1088题:1088 Rational Arithmetic (20分)

#include<vector>
#include<iostream>
#include<math.h>
#include<string>
#include<algorithm>
#include<string>
using namespace std;
long long gcd(long long a, long long b) {
	if (b == 0) return a;
	else return gcd(b, a%b);
}
string simple(long long  a, long long b) {
	string ans;
	if ((a > 0 && b < 0) || (a < 0 && b>0))ans = "-";
	a = abs(a);
	b = abs(b);
	if (a == 0)return "0";
	if (b == 0)return "Inf";
	long long t = gcd(a, b);
	a /= t;
	b /= t;
	long long z = a / b;
	a -= z * b;
	if (z > 0 && a > 0) {
		ans += to_string(z) + " " + to_string(a) + "/" + to_string(b);
	}
	else if (z > 0) {
		ans += to_string(z);
	}
	else {
		ans += to_string(a) + "/" + to_string(b);
	}
	if (ans[0] == '-')return "(" + ans + ")"
	else return ans;
}
int main() {;
	long long a1, a2, b1, b2;
	scanf("%lld/%lld %lld/%lld", &a1, &a2, &b1, &b2);
	string s1 = simple(a1, a2);
	string s2 = simple(b1, b2);
	printf("%s + %s = %s\n", s1.c_str(), s2.c_str(), simple(a1*b2 + b1 * a2, a2*b2).c_str());
	printf("%s - %s = %s\n", s1.c_str(), s2.c_str(), simple(a1*b2 - b1 * a2, a2*b2).c_str());
	printf("%s * %s = %s\n", s1.c_str(), s2.c_str(), simple(a1*b1, a2*b2).c_str());
	if(abs(b1)==0)printf("%s / %s = Inf\n", s1.c_str(), s2.c_str());
	 else printf("%s / %s = %s\n", s1.c_str(), s2.c_str(), simple(a1*b2, a2*b1).c_str());
	return 0;
}

近几年每次基本上都要考一个 字符串运用的题目。

近几年的大趋势是模板题越来越少了,以前很多题目都是固定套路,后面的题目反而简单,虽然看起来复杂一些。

近几年题目基本上都是给你一个概念, 让你读题理解,然后再利用已知知识去自由发挥emm,所以背解题模板没有用,背代码也没有用,只有通过自己不断的去理解各种知识,真正掌握熟练了才是王道。

评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值