首页 > 其他分享 >Codeforces Round #753 (Div. 3)(ABCDE)

Codeforces Round #753 (Div. 3)(ABCDE)

时间:2023-01-20 00:22:20浏览次数:45  
标签:753 int s1 ABCDE cin 负数 用个 ++ Div

A. Linear Keyboard

题意:

给26个字母代表你的键盘(没错你的键盘键位是一行)

再给你一个字符串,问你打出这个字符串需要消耗多少距离

思路:

前面几个数据键位没乱当然不用管,主要是如何处理乱序键位

就用个map来映射就完事了,把乱序的字母映射到26个正序字母上即可

后面套上map后的处理就跟没乱序一样了

代码:

void solve()
{
	map<char,char> mp;
	int ans = 0;
	string s1,s2;
	cin >> s1;
	cin >> s2;
	char x = 'a';
	for(int i = 0;i < 26;i++)
	{
		mp[s1[i]] = (char)x;
		x++;
	}
	for(int i = 0;i < s2.size() - 1;i++)
	{
		// cout << abs(mp[s2[i]] - mp[s2[i + 1]]) << endl;
		ans += abs(mp[s2[i]] - mp[s2[i + 1]]);
	}
	cout << ans << endl;
}

总结:

没啥说的,水题

B. Odd Grasshopper

题意:

给一个起始点x,要跳跃k次

从时间1开始,每秒跳当前时间的距离

如果当前脚下是奇数,向正半轴跳,如果是负数,向负半轴跳

思路:

经过简单模拟,得出了一个假规律(

主要是脑补了一个很对称的规律:向左跳1格,向右跳2格,向左跳3格,向右跳4格.......

但是但是,写完了发现对不上样例,这时才发现规律找假了(

然后又模拟了一遍找规律:

发现每4次跳跃后都会回到原点

那我们就只用考虑后面0-3秒怎么跳的了

模拟一下即可

代码:

void solve()
{
	int x,k,op;
	cin >> x >> k;
	temp = k % 4;
	op = k - temp + 1;
	while(temp--)
	{
		if(x&1) x += op;
		else x -= op;
		op++;
	}
	cout << x << endl;
}

总结:

找规律环节千万不要脑补,是啥规矩就是啥规律(

最好把样例全部模拟一遍再开始写代码

C. Minimum Extraction

题意:

给n个数,每次能去掉数组中的最小的数,然后让所有数减去这个数

问最后能剩下的最小数的最大值是多少

思路:

一开始想的是负数是好东西啊,减一个就能加

然后就把负数和正数分开来算,想先算负数的,再算正数的

其实这里我就犯了一个很大的错误

就是每次减去一个负数,负数也会变大的,甚至减去最小的负数的话整体就没负数了

然后是关于正数的处理也很犯病(

用个vector来模拟,还用了erase和pop

就每次判断最大值减最小值是否大于最小值

但是这样弄显然是不对的,就算后面用个变量来模拟也很难对(

正确做法就是:

先考虑暴力,排完序以后减去最小值,更新右边的所有值,然后继续

但是暴力肯定过不了,想个优化

优化就是其实不用每次都更新后面的所有值,只要用个变量来记录即可

然后每次值再加上这个变量,用个ans变量来记录最大值

就能$O(n)$地解决这个问题

代码:

void solve()
{
	cin >> n;
	vector<int> a(n + 1);
	for(int i = 1;i <= n;i++) cin >> a[i];
	sort(all(a));
	int x = 0,ans = a[1];
	for(int i = 1;i <= n;i++)
	{
		a[i] += x;
		x -= a[i];
		ans = max(ans,a[i]);
	}
	cout << ans << endl;
}

总结:

对于求最大值最小值问题大可不必用个条件来判断退出,这样很容易WA

可以直接用个maxn或者minn来记录,跑完整个数组即可

先考虑暴力再考虑优化,不然容易错得离谱(((((

vector的erase和pop少用,一般用变量标记即可,这两个玩意太容易re了

D. Blue-Red Permutation

题意:

给n个数字,再给n个字符来决定这个数字能向上还是向下变化

问是否能让这n个数字变成1到n的序列(不需要排序)

思路:

最开始想的是弄个差分数组

然后统计出1到n每个位置能变的次数

后来发现没卵用(

随便交了一发贪心居然过了((

贪心思路就是:

排序,先看字符是啥,把字符B全部放在前面

然后字符相同的话数字升序排序

由于是组成一个排列,所以每个元素都是一一对应的

所以这个贪心思路显然是可以的

代码:

bool cmp(pair<int,char> x,pair<int,char> y)
{
	if(x.se == y.se) return x.fi < y.fi;
	else return x.se < y.se;
}
 
void solve()
{
	cin >> n;
	vector<pair<int,char>> a(n + 1);
	for(int i = 1;i <= n;i++) cin >> a[i].fi;
	for(int i = 1;i <= n;i++) cin >> a[i].se;
	sort(all(a),cmp);
	// for(int i = 1;i <= n;i++) cout << a[i].fi << " " << a[i].se << endl;
	int idx = 1;
	for(int i = 1;i <= n;i++)
	{
		if(a[i].fi < idx&&a[i].se == 'B')
		{
			NO;
			return;
		}
		else if(a[i].fi > idx&&a[i].se == 'R')
		{
			NO;
			return;
		}
		idx++;
	}
	YES;
}

总结:

先把思路想通了再写代码

贪心比较玄学,多试试,能对上样例的话再考虑证明(

E. Robot on the Board 1

题意:

给出一个机器人的行动轨迹和场地大小n和m

让你判断在哪个点能执行最多的命令

思路:

当时第一眼感觉就是先求出每个方向的最大值

然后我求出来了

然后就不知道干啥了(

惯例,先想想暴力思路

每个点都模拟一遍那个路线,然后选出适合的

优化方案就是:

先求出每个方向的最大值

然后每次都检查一下能否放得下点

就是判断一下需要的横坐标长度$r - l + 1$是否大于本来的横坐标长度$m$

需要的纵坐标长度$d - u + 1$是否大于本来的纵坐标长度$n$

然后记录一下合适的点的坐标:$abs(u) + 1$,$abs(l) + 1$

一旦不满足条件了就直接break然后输出记录的上一个点即可

代码:

void solve()
{
	string s1;
	cin >> n >> m;
	cin >> s1;
	int x = 0,y = 0,l = 0,r = 0,u = 0,d = 0,q1 = 1,q2 = 1;
	for(auto it : s1)
	{
		if(it == 'L') y--;
		else if(it == 'R') y++;
		else if(it == 'U') x--;
		else x++;
		l = min(l,y);
		r = max(r,y);
		u = min(u,x);
		d = max(d,x);
		if(r - l + 1 > m||d - u + 1 > n) break;
		q1 = abs(u) + 1;
		q2 = abs(l) + 1;
		// cout << q1 << " " << q2 << endl;
	}
	// cout << endl;
	cout << q1 << " " << q2 << endl;
	// cout << l << " " << r << " " << u << " " << d << endl;
}

总结:

一般有很多个答案不知道咋个取答案的就是用缩小区间的方法

最小区间+1就是要的答案

标签:753,int,s1,ABCDE,cin,负数,用个,++,Div
From: https://www.cnblogs.com/rickly233/p/17062342.html

相关文章

  • 「解题报告」ARC141D Non-divisible Set
    很有意思的题,我又没想到咋做。值域为\(2m\),我们要找出一个大小为\(m\)的好集合,我们可以先来分析这个好集合的大小的上界是多少。我们可以猜测一波上界就是\(m\)。可......
  • Codeforces Round #804 (Div. 2)
    题目链接A核心思路也是一个观察性质的过程,但是这个性质比较简单。我们可以发现两个数相等的时候比较好构造。并且我们取另外一个数为1就好了。//Problem:A.TheThir......
  • Codeforces Round #820 (Div. 3) A~F泛做
    一套题学到不少东西A.TwoElevators模拟#include<bits/stdc++.h>usingnamespacestd;#defineendl'\n'#definecerr(x)std::cerr<<(#x)<<"is"<<(x)<<......
  • [CSS]背景图片很大,根据屏幕缩小适配后,div之间有空隙的问题
    RT。美术给的素材宽度是1080px的。在不缩放的情况下,1080px宽度的屏幕显示div之间正常,没有空隙,但使用transform属性之后,div缩小,div之间有空隙(白线) 百度有人说给这些div......
  • 2023牛客寒假算法基础集训营2 ABCDEFHJKL
    比赛链接A题解知识点:数学。用\(n\)减去区间1的端点得到匹配的一个区间,求一下与区间2的交集。一个小公式,两区间\([L_1,R_1]\)和\([L_2,R_2]\)的交集长度为\(\ma......
  • Codeforces Round #807 (Div. 2)
    题目链接A核心思路排序加贪心就好了。//Problem:A.MarkthePhotographer//Contest:Codeforces-CodeforcesRound#807(Div.2)//URL:https://codeforces.......
  • Div高度控制问题
    做网页时尽量是不用设置固定高度的,这样拓展起来更灵活,如果非要设固定高度,就有一些需要注意的地方。IE6和IE7对CSS的解释存在很多差别,今天谈其中一点:height。例子:<div......
  • Codeforces Round #834 (Div. 3) A~E泛做
    A.Yes-Yes?构造一个\(N=50\)的字符串,判断是不是子串即可。#include<bits/stdc++.h>usingnamespacestd;#defineendl'\n'#definecerr(x)std::cerr<<(#x)<<......
  • 解决img和div高度不同的问题(转)
    原文:https://blog.csdn.net/qq_34466755/article/details/1114119861、问题img在div中会在底部产生额外的空隙<body><style>div{color:#fff;......
  • 前端:flex:弹性盒子属性如何使用,实现div在div内水平垂直居中,div显示在一行,div之间间隔相
    前端:flex:弹性盒子属性如何使用在html中多个div是换行显示的,如果我要一行显示多个div盒子怎么办?这里离我可用float是可以实现的,但是今天我们讲讲flex直接上效果图谷咕咕用......