【C++】AcWing 第50周周赛详解

115 篇文章 3 订阅
20 篇文章 0 订阅

4416. 缺少的数

给定一个长度为 n−1 的数列 a1,a2,…,an−1。
数列中的元素两两不同,且都在 1∼n 的范围内。
请你计算,1∼n 中的哪一个数没有在数列中出现过。
输入格式
第一行包含一个整数 n。
第二行包含 n−1 个整数 a1,a2,…,an−1。
输出格式
输出 1∼n 中没有在数列中出现过的数。

思路
1~n求和,减去现有的元素之和就是没有出现过的数

#include <bits/stdc++.h>
#define int long long
using namespace std;
signed main()
{
	int n;
	cin>>n;
	int m=n*(n+1)/2;
	for(int i=0;i<n-1;i++)
	{
		int x;
		cin>>x;
		m-=x;
	}
	cout<<m<<endl;
	return 0;
}

4417. 选区间

给定 n 个一类区间 (l1,i,r1,i)。
给定 m 个二类区间 (l2,i,r2,i)。
请你从一类区间中挑选一个区间,从二类区间中挑选一个区间。
要求,选出的两个区间之间的距离尽可能大。
请你输出最大可能距离。
关于两区间 (l1,r1) 和 (l2,r2) 之间的距离,我们规定:
如果两区间存在交集,则区间距离为 0。
如果两区间不存在交集,则区间距离为 |i−j| 的最小可能值,其中 l1≤i≤r1,l2≤j≤r2。
输入格式
第一行包含一个整数 n。
接下来 n 行,每行包含两个整数 l1,i,r1,i。
再一行包含一个整数 m。
最后 m 行,每行包含两个整数 l2,i,r2,i。
输出格式
一个整数,表示最大可能距离。

思路:

在这里插入图片描述
红色为第一类区间,蓝色为第二类区间
要求区间最大距离无非两种情况(有交集距离为0)

  1. 蓝色左端点的最大值 - 去红色右端点的最小值
  2. 红色左端点最大值蓝 - 色右端点的最小值
    最后取max即可
#include <bits/stdc++.h>
#define int long long
using namespace std;
int n,m;
signed main()
{
	cin>>n;
	int maxv1=0,minv1=0x3f3f3f3f;
	while(n--)
	{
		int l,r;
		cin>>l>>r;
		maxv1=max(maxv1,l);
		minv1=min(minv1,r);
	}
	cin>>m;
	int res=0;
	while(m--)
	{
		int l,r;
		cin>>l>>r;
		if(r<maxv1)res=max(res,maxv1-r);
		if(l>minv1)res=max(res,l-minv1);
	}
	cout<<res<<endl;
	return 0;
}

4418. 选元素

给定一个长度为 n 的整数序列 a1,a2,…,an。
请你从中挑选 x 个元素,要求:
原序列中的每一个长度为 k 的连续子序列都至少包含一个被选中的元素。
满足条件 1 的前提下,所选 x 个元素的相加之和应尽可能大。
输出最大可能和。
输入格式
第一行包含三个整数 n,k,x。
第二行包含 n 个整数 a1,a2,…,an。
输出格式
如果无法满足题目要求,则输出 −1。
否则,输出一个整数,表示所选元素的最大可能和。

在这里插入图片描述
思路
每一个长度为 k 的连续子序列都至少包含一个被选中的元素<=>选择的两个数之间距离不超过k-1,
f[i][j]:从所有前i个数中选,且第i个数被选的所有方案最大值
最后需要注意的是:后n-k+1个数的选择与不选择会影响前边的数选与不选,所以需要枚举后n-k+1个数求max为最终结果

#include <bits/stdc++.h>
using namespace std;
#define int long long
const int N=310;
int n,k,m;
int f[N][N];
signed main()
{
	cin>>n>>k>>m;
	memset(f,-0x3f,sizeof f);
	f[0][0]=0;
	for(int i=1;i<=n;i++)
	{
		int x;
		cin>>x;
		for(int j=1;j<=m;j++)
		{
			for(int u=max(i-k,0ll);u<i;u++)
				f[i][j]=max(f[i][j],f[u][j-1]+x);
		}
	}
	int res=-1;
	for(int i=n-k+1;i<=n;i++)
	{
		res=max(res,f[i][m]);
	}
	cout<<res<<endl;
	return 0;
}
  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

leimingzeOuO

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值