Codeforces 1133E - K Balanced Teams - [DP]
题目链接:https://codeforces.com/contest/1133/problem/C
题意:
给出 $n$ 个数,选取其中若干个数分别组成 $k$ 组,要求每组内最大值与最小值的差值不超过5,求 $k$ 组合起来最多可以放多少个数。
题解:
将 $a[1 \sim n]$ 从小到大排序,排序后每个组必定可以视为数组 $a$ 上一段连续区间,
$f[i][j]$ 表示到第 $i$ 个数为止,前面组成 $j$ 组,最多可以包含多少个数。
那么,考虑第 $i$ 个数选取与否,如果不选,那么 $f[i][j]=f[i-1][j]$;
如果选,那么必然是第 $i$ 个数所在组人数加上前面那些组人数,假设 $p$ 表示距离 $a[i]$ 左侧最远的那个位置(满足 $a[i]-a[p] \le 5$),$f[i][j]=(i-p+1)+f[p-1][j-1]$。
AC代码:
用lower_bound找 $p$,时间复杂度 $O(n \log n + nk)$。
#include<bits/stdc++.h>
using namespace std;
const int maxn=;
int n,k,ans;
int a[maxn];
int f[maxn][maxn];
int main()
{
ios::sync_with_stdio();
cin.tie(), cout.tie(); cin>>n>>k;
for(int i=;i<=n;i++) cin>>a[i];
sort(a+,a+n+); ans=f[][]=;
for(int i=;i<=n;i++)
{
int p=lower_bound(a+,a+i+,a[i]-)-a;
for(int j=;j<=min(k,i);j++)
{
f[i][j]=max(f[i-][j],(i-p+)+f[p-][j-]);
ans=max(ans,f[i][j]);
}
}
cout<<ans<<endl;
}
线性维护 $p$,时间复杂度 $O(nk)$。
#include<bits/stdc++.h>
using namespace std;
const int maxn=;
int n,k,ans;
int a[maxn];
int f[maxn][maxn];
int main()
{
ios::sync_with_stdio();
cin.tie(), cout.tie(); cin>>n>>k;
for(int i=;i<=n;i++) cin>>a[i];
sort(a+,a+n+); ans=f[][]=;
int p=;
for(int i=;i<=n;i++)
{
while(p<i && a[i]-a[p]>) p++;
for(int j=;j<=min(k,i);j++)
{
f[i][j]=max(f[i-][j],(i-p+)+f[p-][j-]);
ans=max(ans,f[i][j]);
}
}
cout<<ans<<endl;
}
Codeforces 1133E - K Balanced Teams - [DP]的更多相关文章
- Codeforces 544E K Balanced Teams (DP)
题目: You are a coach at your local university. There are nn students under your supervision, the prog ...
- codeforces 1133E K Balanced Teams
题目链接:http://codeforces.com/contest/1133/problem/E 题目大意: 在n个人中找到k个队伍.每个队伍必须满足最大值减最小值不超过5.求满足条件k个队伍人数的 ...
- Codeforces Round #544 (Div. 3) E. K Balanced Teams (DP)
题意:有\(n\)个人,每个人的能力值是\(a_i\),现在你想将这些人分成\(k\)组(没必要全选),但是每组中最高水平和最低水平的人的能力差值必须\(\le 5\),问最多能选多少人. 题解:想了 ...
- CF1133E K Balanced Teams(DP)
/* 排序之后每个点往前能选择的是一段区间, 所以我们实际上转移位置是确定的 然后f[i][j]表示到了i选了j段的最大贡献, 显然状态数是O(n^2)的, 转移是O(1)的 */ #include& ...
- 【CF1133E】K Balanced Teams(动态规划,单调队列)
[CF1133E]K Balanced Teams(动态规划,单调队列) 题面 CF 让你把一堆数选一些出来分成不超过\(K\)组,每一组里面的最大值和最小值之差不超过\(5\),求最多有多少个人元素 ...
- K Balanced Teams CodeForces - 1133E (Dp)
题意: 给出 n 个数,选取其中若干个数分别组成至多 k 组,要求每组内最大值与最小值的差值不超过5,求最后被选上的总人数. 题解: 将a[1∼n] 从小到大排序, f[i][j] 表示到第 i 个数 ...
- E. K Balanced Teams
类比背包问题,为每个学生附加一个权重$pos[i]$,意思是选择该学生后,之后可以选择$p[i]~p[i]+5$的学生. 转换公式: $$d[i][j]=max(d[i+1][q],d[i+pos][ ...
- Codeforces Round #598 (Div. 3) E. Yet Another Division Into Teams dp
E. Yet Another Division Into Teams There are n students at your university. The programming skill of ...
- Codeforces 1108D - Diverse Garland - [简单DP]
题目链接:http://codeforces.com/problemset/problem/1108/D time limit per test 1 secondmemory limit per te ...
随机推荐
- Windows中点击“关闭”button发生了什么?
对于Windows操作,当用户点击"关闭"button时,窗体函数就会收到一个WM_DESTROY消息. 窗体函数应该调用PostQuitMessage(0) 向消息队列插入一个W ...
- Boltzmann 玻尔兹曼机(BM)
Hopfield + 模拟退火 ⇒ Boltimann machine(随机神经网络),由 Hinton 和他的长期合作者 Sejnowski(Hopfield 的博士生) 共同提出. 1. 基本公式 ...
- Matlab随笔之求解线性方程
原文:Matlab随笔之求解线性方程 理论知识补充: %矩阵除分为矩阵右除和矩阵左除. %矩阵右除的运算符号为“/”,设A,B为两个矩阵,则“A/B”是指方程X*B=A的解矩阵X. %矩阵A和B的列数 ...
- CCPlace,CCFlip*,CCToggleVisibility,CCMoveTo*,CCJumpTo*,CCScale*,CCRotate*,CCSkew*,fade,CCCardinalSp*
1 CCAction动作 CCAction作为一个基类.事实上质是一个接口(即抽象类),由它派生的实现类(如运动和转动等)才是我们实际使用的动作.CCAction 的绝大多数实现类都派生自CCF ...
- OpenExpressApp:精通 WPF UI Virtualization
原文:OpenExpressApp:精通 WPF UI Virtualization 本篇博客主要说明如何使用 UI Virtualization(以下简称为 UIV) 来提升 OEA 框架中 Tre ...
- 【转载】MySQL双主双从高可用集群架构
双浮动VIP 原文地址:http://www.linuxcache.com/archives/2907 转载请注明原文地址.
- CheckBox IsHitTestVisible
<Grid> <Grid.ColumnDefinitions> <ColumnDefinition Width="Auto"></Colu ...
- C# IDisposable接口的使用
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.T ...
- window对象的方法
window.alert('大家好!');//弹出警告对话框 window.confirm('确定要删除吗?');//确定.取消对话框,返回true或false; window.navigate(ur ...
- 快速写入Xml文件
我们在做一些操作的时候会需要生成日志,Xml文件就是我们常用的一种日志文件. 普通操作Xml文件的代码遇到大数据量的话就很慢了. 用这个生成Xml文件的话,即使数据量很大,也很快 private vo ...