poj 2576 动态规划

题目描述:

n个人,每个人体重x[i],让你把他们分成两组,两组之间的人数差不能大于1。输出两组体重差最小的情况。

解题报告:

dp

dp[i] = 1,表示体重和为i可以达到。

mark[i][j] = 1,表示i个人可以构成体重j.

代码:

#include<iostream>
#include<fstream>
#include<cmath>

using namespace std;

int n;
int dp[45001];
int mark[101][45001];
int a[101];

void read(){
//    ifstream cin("in.txt");
    int i,j,k;
    int sum=0;
    cin>>n;
    for(i=1;i<=n;i++)
    {
        cin>>a[i];
        sum+=a[i];
    }
    if(n==1)
    {
        cout<<0<<' '<<a[1]<<endl;
        return;
    }
    dp[a[1]]=1;
    mark[1][a[1]]=1;
    dp[0]=1;
   
    for(i=2;i<=n;i++)
    {
        for(j=sum;j>=a[i];j--)
            if(dp[j-a[i]])
            {
                dp[j]=1;
                if(j==a[i])
                    mark[1][j]=1;
                else
                for(k=1;k<=i-1;k++)
                    if(mark[k][j-a[i]])
                        mark[k+1][j]=1;
            }
    }
    int ans=450000;
    for(i=1;i<=sum;i++)
        if(mark[n/2][i]&&ans>abs(sum-i-i))
        {
            ans=abs(sum-i-i);
            j=i;
        }
    if(j>sum/2)
        j=sum-j;
    cout<<j<<' '<<sum-j<<endl;
           

}

int main(){
    read();
    return 0;
}

posted on 2011-02-23 12:11  宇宙吾心  阅读(445)  评论(0)    收藏  举报

导航