【poj1837】Balance

这个题我们可以把它转化成01背包,因为阻力臂*阻力=动力臂*动力(初中物理),所以说要使两方平衡,二者绝对值要保持一致。所以说可能会出现负数,那么我们将所有的数统一加上一个值,因为-15<=c[i]<=15, w[i]<=25,g<=20,所以绝对值最大为15*25*20=7500,因此统一加上7500,就可以转化成01背包了

#include<iostream>
#include<cstring>
#include<cstdio>
#include<cmath>
using namespace std;
int c,g,c1[25],w[25],t,dp[2][15010];
int main()
{
    scanf("%d%d",&c,&g);
    for(int i=1;i<=c;i++)
        scanf("%d",&c1[i]);
    for(int i=1;i<=g;i++)
        scanf("%d",&w[i]);
    dp[0][7500]=1;
    for(int i=1;i<=g;i++)//一定要先枚举物品,因为多个物品可以对应一个挂钩 
    {
        t=1-t;//滚动数组优化 
        for(int j=0;j<=15000;j++)
            dp[t][j]=0;
        for(int j=0;j<=15000;j++)
        {
            if(dp[1-t][j])//如果上一次选取物品的时候得到平衡度为j的时候 
            {
                for(int k=1;k<=c;k++)//再去进行转移 
                    dp[t][j+c1[k]*w[i]]+=dp[1-t][j];
            }
        }
    }
    printf("%d",dp[t][7500]);//默认设置平衡时,平衡度为7500 
}

 

posted @ 2017-10-31 14:01  那一抹落日的橙  阅读(103)  评论(0编辑  收藏  举报