CF1714

发布于 2022-08-02  717 次阅读


碎碎念

没想到人生第一份兼职是信奥助教,通知到我的时候就只剩7天了?!

《重生之七日成神》正式开始(

Day1

时隔一年多,浅浅打开一下洛谷,一切的一切都是那么熟悉(除了名字变成了灰色)

随机跳题不是紫题黑题就是橙题黄题,两极分化有点严重哈

由于七日后的教学水平是提高-,我选择了黄题(

就做了两题,还分别错了一次(无能狂怒)

Day2

早上中午起来又打开了洛谷,名字变橙了,不错不错

想起学姐说的大二cf不上橙就等死,俺又打开了cf

发现今天晚上有一场div3(正好适合我)

琢磨了半天,这个五年前注册的号终于第一次报名了比赛(

两个小时十五分钟,七道题只做了前五题,很好,已经是个废物了

Day3

整了一个白天,博客也重生了(bushi

从三年前的虚拟主机变成了现在的云服务器

从.top变成了.cn,从小琳变成了小泠(

顺便还换了个主题,当代忒修斯之船了属于是

(唯一没变的就是懒得备案,还在香港)

再上cf的时候,发现rating涨了598分(好耶!)

今日计划:补完剩下的两道题,并写完题解

--------碎碎念到此结束,下面是正文(手动分割线)--------

别问,问就是没写,开摆

A - Everyone Loves to Sleep

给定若干个二十四小时制的闹钟时间和睡觉时间

询问能睡多久

solution

可以全部换算成分钟,小于睡觉时间的加1440等于到了第二天

#include<bits/stdc++.h>
using namespace std;
int T,n,h,m;
int main()
{
	scanf("%d",&T);
	while(T--)
	{
		scanf("%d%d%d",&n,&h,&m);
		int ti=h*60+m,ans=10000;
		for(int i=1;i<=n;i++)
		{
			scanf("%d%d",&h,&m);
			int tii=h*60+m;
			if(tii>=ti)ans=min(ans,tii-ti);
			else ans=min(ans,tii-ti+1440);
		}
		printf("%d %d\n",ans/60,ans%60);
	}
	return 0;
}

B - Remove Prefix

删掉左边多少个数才能使整个序列的数都不同

solution

右边开始找第一个相同的数即可

#include<bits/stdc++.h>
using namespace std;
int T,n,a[200010],p[200010];
int main()
{
	scanf("%d",&T);
	while(T--)
	{
		scanf("%d",&n);
		for(int i=1;i<=n;i++)
			scanf("%d",&a[i]);
		int pos=0;
		for(int i=n;i>=1;i--)
		{
			if(p[a[i]]){pos=i;break;}
			p[a[i]]++;
		}
		for(int i=pos+1;i<=n;i++)
			p[a[i]]--;
		printf("%d\n",pos);
	}
	return 0;
}

C - Minimum Varied Number

找出数码和为 s 的最小数字,使得其中的所有数字都是不同的(即所有数字都是唯一的)

solution

末尾从9开始枚举即可

#include<bits/stdc++.h>
using namespace std;
int T,s;
long long ans;
void get(int n)
{
	if(n==0)return;
	if(s>=n)
	{
		s-=n;
		get(n-1);
		ans=ans*10+n;
	}
	else get(n-1);
	return;
}
int main()
{
	scanf("%d",&T);
	while(T--)
	{
		scanf("%d",&s),ans=0;
		get(9);
		printf("%lld\n",ans);
	}
	return 0;
}

D - Color with Occurrences

给定一段黑色文本 t 和多个字符串 s1​,s2​...sn​。

一次操作可以将 t 中任意一个与任意 s 相等的子串涂成红色。两次涂红的字母仍然是红色。s 没有使用次数限制。求全涂成红色最小次数和方案,任意输出一种解。

solution

每个点都是一定要涂色的,那么对于每个点暴力寻找

找到当前点能涂色到的最远位置,一定最优

#include<bits/stdc++.h>
using namespace std;
int T,n,len,ret,ans,l[11];
char a[110],s[11][11];
void solve(int nw)
{
	if(ret<0)return;
	if(nw==len){ret=1;printf("%d\n",ans);return;}
	int nxt=-1,w,p;
	for(int i=1;i<=n;i++)
	{
		for(int j=0;j<l[i];j++)
		{
			if(j>nw)continue;
			if(nw+l[i]-j>len)continue;
			int chk=0;
			for(int k=0;k<l[i];k++)
				if(a[nw+k-j]!=s[i][k]){chk=1;break;}
			if(chk)continue;
			if(nw+l[i]-j>nxt)
			{
				nxt=nw+l[i]-j;
				w=i;
				p=nw-j;
			}
		}
	}
	if(nxt==-1){ret=-1;printf("-1\n");return;}
	ans++,solve(nxt);
	if(ret>0)
	{
		printf("%d %d\n",w,p+1);
	}
}
int main()
{
	scanf("%d",&T);
	while(T--)
	{
		scanf("%s%d",a,&n),len=strlen(a);
		for(int i=1;i<=n;i++)
			scanf("%s",s[i]),l[i]=strlen(s[i]);
		ret=0,ans=0,solve(0);
	}
	return 0;
}

E - Add Modulo 10

对每组数据,你可以对其作若干次(可以为零)如下操作:

选取数据中的一个数 ai​ 将其替换为 ai​+(ai ​mod 10)

问经过若干次变换后,该组数据能否全部相同

solution

可以发现1,3,5,7为一组,2,4,6,8为一组,5,0为一组,判断即可

#include<bits/stdc++.h>
using namespace std;
int T,n,x,y,tag,ret,a[30];
int main()
{
	scanf("%d",&T);
	while(T--)
	{
		tag=-1,ret=-1;
		memset(a,0,sizeof(a));
		scanf("%d",&n);
		for(int i=1;i<=n;i++)
		{
			scanf("%d",&x),y=x%10;
			if(y==1||y==3||y==7||y==9)
			{
				ret=1;
				x+=y,x%=20,a[x]++;
			}
			else if(y==0||y==5)
			{
				x+=y;
				if(tag==-1)tag=x;
				else if(tag!=x)tag=-2;
			}
			else
			{
				ret=1;
				x%=20,a[x]++;
			}
		}
		if(tag==-2)printf("No\n");
		else if(tag!=-1)
		{
			if(ret>0)printf("No\n");
			else printf("Yes\n");
		}
		else
		{
			int pa=a[2]+a[4]+a[8]+a[16];
			int pb=a[12]+a[14]+a[18]+a[6];
			if(pa==0||pb==0)printf("Yes\n");
			else printf("No\n");
		}
	}
	return 0;
}