【解题报告】CF DIV3 #ROUND 710 A~E

【解题报告】CF DIV3 #ROUND 710 A~E

比赛链接

A.Strange Table

思路
一眼题,希望校园网给力些
代码

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
int T;

signed main()
{
    cin>>T;
    while(T--)
    {
        ll n,m,x;
        cin>>n>>m>>x;
        ll a=(x-1)%n,b=(x-1)/n+1;
        cout<<a*m+b<<endl;
    }
    return 0;
}

B. Partial Replacement

题意:
距离限制,相邻x距离不能超过给定值k,而且第一个和最后一个‘*’必须改成‘x’。可以把‘*’改成‘x’,但是’.'不行。问最少改几个满足条件。

思路
又被B杀了
原本想的是尽可能要减少改的次数,那么让相邻x距离尽可能大然后我就直接每次跳k个距离看是不是‘*’是的话就改,不是的话就不管,然后最后检查以下最后一个有没有改掉,没有的话补一个。
这样就出现了一个问题,对于某一个与前一个‘x’距离小于k的‘*’如果你不改的话,可能以后就没有’*‘来改,这样可能导致和后面的x距离差距太大了。说的直白一些就是说了有这个限制,你要是一直贴着这个边干的话,未来可能稍有不顺,你就没了。

然后看了看官方题解,发现:不是“*”的话就不管,这么干是不对的,应该再往前找找有没有需要改变的。

所以正确的贪心描述是:在最多能跨k距离的情况下,寻找里左端点最远的’*'修改
代码

#include<bits/stdc++.h>
using namespace std;
#define endl "\n"
typedef long long LL;

/*DATA & KEY



*/
int T;
void solve(int T)
{
	//NEW DATA CLEAN
	
	//NOTE!!!
	int n,k,ans;
	ans=1;
	string s;
	cin>>n>>k>>s;
	
	int l=s.find_first_of('*');//第一次知道有这玩意
	while (true) 
	{
	    int j = min(n - 1, l + k);
	    for (; l < j && s[j] == '.'; j--) {}//逆向找,来实现
	    if (l == j) {
	      break;
	    }
	    ans++;
	    l = j;//更新左端点
	}
  	cout<<ans<<endl;
	
}

int main()
{
	scanf("%d",&T);
	while(T--)solve(T);
	return 0;
}

C.Double-ended Strings

题意
给两个串,四个操作,可以选择把a或b首或者尾字母删掉,问最少操作多少次可以让a和b相等
思路
比较裸的求最长公共子串(不是子序列啊啊啊)
i f ( a [ i ] = = b [ j ] ) d p [ i ] [ j ] = d p [ i − 1 ] [ j − 1 ] + 1 if(a[i]==b[j])dp[i][j]=dp[i-1][j-1]+1 if(a[i]==b[j])dp[i][j]=dp[i1][j1]+1其他的 d p [ i ] [ j = 0 dp[i][j=0 dp[i][j=0
不过数据量挺小的也可以拿BFS做
代码

#include<bits/stdc++.h>
using namespace std;
#define endl "\n"
typedef long long LL;
const int N=25;
int T;
int f[N][N];

void solve()
{
	int maxcom=0;
	memset(f,0,sizeof f);
	char a[N],b[N];
	cin>>(a+1)>>(b+1);
	int la=strlen(a+1),lb=strlen(b+1);
	for(int i=1;i<=la;i++)
		for(int j=1;j<=lb;j++)
		{
			if(a[i]==b[j])f[i][j]=f[i-1][j-1]+1;
			else f[i][j]=0;
			maxcom=max(maxcom,f[i][j]);
		}
	
	cout<<la+lb-2*maxcom<<endl;
}

int main()
{
	scanf("%d",&T);
	while(T--)solve();
	return 0;
}

D.Epic Transformation

思路
又是分组配对问题,不同数字的可以组成一组,问最多可以组多少组,优先队列动态维护数量最多的那组和其他组一个个配对(不用太跳,一个个来挺不错的,先实现了再考虑优化)
代码

#include<bits/stdc++.h>
using namespace std;
#define endl "\n"
typedef long long LL;

/*DATA & KEY

t 1e4
total n 2e5
ai 1e9

*/

const int N=2e5+10;
int T;
map<int,int>mp;
void solve(int T)
{
	mp.clear();
	int n;
	cin>>n;
	for(int i=0,x;i<n;i++)
	{
		cin>>x;
		mp[x]++;
	}
	priority_queue<int>heap;
	for(auto t:mp)heap.push(t.second);
	while(heap.size()>1)
	{
		int t=heap.top();heap.pop();
		int k=heap.top();heap.pop();
		t--;k--;
		if(t)heap.push(t);
		if(k)heap.push(k);
	}
	if(heap.size())cout<<heap.top()<<endl;
	else cout<<0<<endl;
}

int main()
{
	scanf("%d",&T);
	while(T--)solve(T);
	return 0;
}

E.Restoring the Permutation

思路
字典序最小:直接暴力整一波就够了。主要是字典序最大,如果从后面找<x且没用过的数的话很容易TLE。
找小于x的最大可用的数可以想到使用二分来优化,借助set可以实现这一操作,而且set支持:插入,删除,查找。可以比较好的维护数是否可用,而且本身支持二分查找。
代码

#include<bits/stdc++.h>
using namespace std;
#define endl "\n"
typedef long long LL;

/*DATA & KEY

t: 1 1e4
total n: 1 2e5
q: 1 n

*/

const int N=2e5+10;
int T;
int q[N];
bool st[N];
map<int,int>mp;
void solve(int T)
{
	//NEW DATA CLEAN
	memset(q,0,sizeof q);
	memset(st,0,sizeof st);
	mp.clear();
	//NOTE!!!
	int n;cin>>n;
	
	for(int i=1;i<=n;i++)cin>>q[i];
	for(int i=1;i<=n;i++)mp[q[i]]++;
	
	set<int>s;
	for(int i=1;i<=n;i++)s.insert(-i);
	int k=1;
	for(auto t:mp)
	{
		int x=t.first,y=t.second;
		printf("%d ",x);
		st[x]=1;
		for(int i=1;i<y;i++)
		{
			while(st[k])k++;
			printf("%d ",k);
			st[k]=1;
		}
	}
	puts("");
	for(auto t:mp)
	{
		int x=t.first,y=t.second;
		printf("%d ",x);
		s.erase(-x);
		for(int i=1;i<y;i++)
		{
			auto it=s.upper_bound(-x);
			int tmp=*it;
			printf("%d ",-tmp);
			s.erase(tmp);
		}	
	}
	puts("");
}

int main()
{
	scanf("%d",&T);
	while(T--)solve(T);
	return 0;
}

反思

A:

无他,网快手快

B:

相邻元素最大距离有限制,问最少改几次,满足条件。
最少改几次转化为,每次改的相邻距离尽可能大。

string字符串查找第一个元素的用法

int i=s.find_first_of('*')

C:

两字符串经过系列操作变为相同串最小操作次数,联想到最短编辑距离和最长公共子序列
不过根据操作特点,这题要写最长公共子串而非最长公共子序列。
分清公共子串和公共子序列。
数据量小可以BFS乱搞

D:

多组配对问题,问最多配多少组。
统计每组数量,然后贪心让当前数量最多的和其他组配对
优先队列维护最多组数量。
一个个配对,数据量小不用跳着搞

E:

字典序贪心。
寻找小于x的最大值,联想到二分优化。
set支持排序,二分查找,插入,去重,删除。

python023基于Python旅游景点推荐系统带vue前后端分离毕业源码案例设计 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。
JSP基于SSM网上医院预约挂号系统毕业源码案例设计 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值