Codeforces Round #638 (Div. 2) E思维,,dp

Posted starve

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Codeforces Round #638 (Div. 2) E思维,,dp相关的知识,希望对你有一定的参考价值。

题:

题意:给定n组,每组ai个红果,bi个白果。还给定整数k,代表组成同一盆要达成的数目,同时组成同一盆的水果要么是来自同一组,要么就是有相同颜色,问最大能组成多少盆

分析:初步地,我们可以只是按照颜色来分组,那么答案就是suma/k+sumb/k,那么就剩下不足k个的红果和不足k个的白果,这时我们发现,只要再从剩下的中凑出一组是来自同一组的,那么答案就会加一,而这种方法是最优的。那么我们就想办法让其他组分配合理而让某一组留下尽可能多的白果和红果(因为要让至少有suma/a+sumb/k盆)

   考虑n<=500,那么我们可以枚举o(n^3)要保证至少盆的情况下,我们只能k个k个地加进去,而转移就是暴力地枚举【(1~k-1)+(k-1~1)】

技术图片
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int M=5e2+3;
int dp1[M][M],dp2[M][M];
int a[M],b[M];
int main(){
    ios::sync_with_stdio(false);
    cin.tie(0);
    ll suma=0,sumb=0;
    int n,k;
    cin>>n>>k;
    for(int i=1;i<=n;i++)
        cin>>a[i]>>b[i],suma+=a[i],sumb+=b[i];
    ll yua=suma%k,yub=sumb%k;
    if(yua+yub<k){
        return cout<<suma/k+sumb/k,0;
    }
    dp1[k][0]=dp1[0][k]=1;
    for(int i=1;i<=n;i++){
        for(int j=0;j<=k;j++)
            for(int p=0;p<=k;p++)
                dp2[i][j]=0;
        for(int j=0;j<=k;j++)
            dp2[j][k-j]=dp1[j][k-j];
        for(int l=1;l<k;l++){
            int r=k-l;
            if(l<=a[i]&&r<=b[i]){
              //  cout<<"!!"<<l<<‘ ‘<<r<<endl;
                for(int j=0;j<=k;j++){
                    dp2[(j+r)%k][(k-j+l)%k]|=dp1[j][k-j];///
                }
            }
        }
        for(int j=0;j<=k;j++)
            dp1[j][k-j]=dp2[j][k-j];
    }
    ll sign=0;
    for(int i=1;i<=yua;i++){
        if(k-i<=yub&&dp2[k-i][i])
            sign=1;
    }
    ///cout<<suma/k+sumb/k<<endl;
    return 0;
}
View Code

 

以上是关于Codeforces Round #638 (Div. 2) E思维,,dp的主要内容,如果未能解决你的问题,请参考以下文章

Codeforces Round #638 (Div. 2)

Codeforces Round #638 (Div. 2)

Codeforces Round #638 (Div. 2)

Codeforces Round #638 (Div. 2)(A~B)

Codeforces Round #638 (Div. 2) A~C题解

CF A. Phoenix and Balance Codeforces Round #638 (Div. 2) 5月1号