参考博客点此
思路:
将每个人的积分用权值表示为cou【i】,即i积分的有cou【i】个人。
把原来人的积分按照积分差为K分组,如:k==2时,2、4、6、8、10…是一组,1、3、5、7、9…是另外一组;
将这K组进行动态规划,求出每组的最大值,而后把各个小组的最大值加起来,就是在线人数中一起匹配所不能匹配任意一场的最多人数。
dp方程:sum[f]=max((time+sum[f-2]),sum[f-1]);
#include<stdio.h>
#include<algorithm>
#include<iostream>
#include<math.h>
#include<string.h>
using namespace std;
int dp[100010],n,k,cou[100010],ans,sum[100010];
int main(){
cin>>n>>k;
for(int i=0;i<n;i++)
cin>>dp[i];
sort(dp,dp+n); //dp【n-1】即为最大值,不用再另做循环求最大值
for(int i=0;i<n;i++){
cou[dp[i]]=cou[dp[i]]+1;//记录各个积分的权值
}
if(k==0){//k为0的情况,特殊处理
for(int i=0;i<=dp[n-1];i++)
if(cou[i]!=0)
ans++;
}
else{//k>0的情况
for(int i=dp[0];i<dp[0]+k;i++){//从最小值开始,分为k个组
int f = 2,time = 0;
for(int j=i;j<=dp[n-1];j+=k)//每个组分别进行动态规划求最大值
{
time = cou[j];
sum[f]=max((time+sum[f-2]),sum[f-1]);
f++;
}
ans+=sum[f-1];//最大值相加
}
}
cout<<ans<<endl;//输出结果
return 0;
}
通过截图