zoukankan      html  css  js  c++  java
  • HDU1171-Big Event in HDU

    描述:

      Nowadays, we all know that Computer College is the biggest department in HDU. But, maybe you don't know that Computer College had ever been split into Computer College and Software College in 2002. 

      The splitting is absolutely a big event in HDU! At the same time, it is a trouble thing too. All facilities must go halves. First, all facilities are assessed, and two facilities are thought to be same if they have the same value. It is assumed that there is N (0<N<1000) kinds of facilities (different value, different kinds). 

      Input contains multiple test cases. Each test case starts with a number N (0 < N <= 50 -- the total number of different facilities). The next N lines contain an integer V (0<V<=50 --value of facility) and an integer M (0<M<=100 --corresponding number of the facilities) each. You can assume that all V are different. 

      A test case starting with a negative integer terminates input and this test case is not to be processed. 

      For each case, print one line containing two integers A and B which denote the value of Computer College and Software College will get respectively. A and B should be as equal as possible. At the same time, you should guarantee that A is not less than B. 

    代码:

      多重背包转化为01背包问题,可以认为在一个容量为所有物品价值累加和的一半的背包中,尽量达到最大值。

      第一版:

    #include<stdio.h>
    #include<string.h>
    #include<iostream>
    #include<stdlib.h>
    #include <math.h>
    #define N 105
    #define M 1000
    using namespace std;
    
    int main(){
        int n,v[N],dp[N][M],a,b,volume,sum;
        while( scanf("%d",&n)!=EOF  && n>0 ){
            volume=0;sum=1;
            for( int i=0;i<n;i++ ){
                scanf("%d%d",&a,&b);
                volume+=(a*b);
                while( b-- )//将单个物品依次加入
                    v[sum++]=a;
            }
            sum--;
            //需要初始化dp中的全部值为0,下一次dp比较的值,上一次可能没有赋值,比较时将与负值(未初始化)进行比较,得到不正确的值
            //for( int i=0;i<volume;i++ )
            //    dp[0][i]=0;
            memset(dp,0,sizeof(dp));
    
            for( int i=1;i<=sum;i++ ){
                for( int j=v[i];j<=volume/2;j++ ){
                    dp[i][j]=max(dp[i-1][j],dp[i-1][j-v[i]]+v[i]);//转移方程
                }
            }
            printf("%d %d
    ",max(dp[sum][volume/2],volume-dp[sum][volume/2]),min(dp[sum][volume/2],volume-dp[sum][volume/2]));
        }
        system("pause");
        return 0;
    }

    测试用例:

    2

    10 1

    20 1

    3

    10 1

    20 2

    30 1

    -1

      测试用例2答案是对的,用例1答案不对。因为对于用例1,20大于总价值一半(15),故dp值均为0,最后结果为0。为此,不妨使用优化版的dp,即使用一维数组dp,这样就算出现刚才的情况,较早的dp值即为答案。

      值得注意的是,背包要求尽量装满,故初始化时需要全部赋值为0(不赋值则出错)。

    #include<stdio.h>
    #include<string.h>
    #include<iostream>
    #include<stdlib.h>
    #include <math.h>
    #define N 105
    #define M 100000
    using namespace std;
    
    int main(){
        int n,v[N],dp[M],a,b,volume,sum;
        while( scanf("%d",&n)!=EOF  && n>0 ){
            volume=0;sum=1;
            for( int i=0;i<n;i++ ){
                scanf("%d%d",&a,&b);
                volume+=(a*b);
                while( b-- )//将单个物品依次加入
                    v[sum++]=a;
            }
            sum--;
            //需要初始化dp中的全部值为0,下一次dp比较的值,上一次可能没有赋值,比较时将与负值(未初始化)进行比较,得到不正确的值
            memset(dp,0,sizeof(dp));
    
            for( int i=1;i<=sum;i++ ){
                for( int j=volume/2;j>=v[i];j-- ){
                    dp[j]=max(dp[j],dp[j-v[i]]+v[i]);//转移方程
                }
            }
            printf("%d %d
    ",max(dp[volume/2],volume-dp[volume/2]),min(dp[volume/2],volume-dp[volume/2]));
        }
        system("pause");
        return 0;
    }
  • 相关阅读:
    HTML5 CSS3简要教程
    WP模拟器修改语言为中文方法
    仿牛华数码频道网整站源码
    backBarButtonItem 颜色/文字修改
    这是html5中WebGL的演示
    CSS3/jQuery创意盒子动画菜单
    bootstrap学习和使用的经验总结
    uploadify插件实现多个图片上传并预览
    绝对炫的幻灯片插件-SKITTER
    制作手机使用的网页图片查看器
  • 原文地址:https://www.cnblogs.com/lucio_yz/p/4722518.html
Copyright © 2011-2022 走看看