HDOJ  2602   Bone Collector

来源:互联网 发布:ubuntu安装qq拼音 编辑:程序博客网 时间:2024/05/28 01:36

题目:http://acm.hdu.edu.cn/showproblem.php?pid=2602

#include<stdio.h>
#include<memory.h>
#define M 1010
int T;
int N;//骨头数量
int V;//背包容量
struct bone{
    intvalue;//骨头价值
    intvolume;//骨头所占背包容量
}bone[M];
int bag[M];
int main(void)
{
   scanf("%d",&T);
   while(T--){
       scanf("%d%d",&N,&V);//读取骨头数量和背包容量
       for(int i=1;i<=N;i++)
           scanf("%d",&bone[i].value);//读取每个骨头的价值
       for(int i=1;i<=N;i++)
           scanf("%d",&bone[i].volume);//读取每个骨头所占背包容量
       memset(bag,0,sizeof(bag));//初始化数组
***************************************************************
       for(int j=1;j<=N;j++)
       {
           for(int i=V;i>=0;i--)
           {//背包从大到小开始搜索是因为,
               //如果从小到大开始搜索,有时会把一块骨头重复搜索两次
               if(i>=bone[j].volume&&bone[j].value
                  +bag[i-bone[j].volume]>bag[i]) //----------(1)
                   //如果背包容量大于骨头所占容量,
                   //且除去背包里与当前骨头所占容量相同的那块骨头
                   //背包里其余骨头的价值,
                   //加上当前骨头的价值大于当前背包里所有骨头的价值,
                   //那么说明当前骨头是最佳选择
                   bag[i]=bone[j].value+bag[i-bone[j].volume];
           }
       }
************************************************************
       printf("%d\n",bag[V]);
    }
    return0;
}
*****************************************
其实中间那一步,可以代替为
for(int j=1;j<=N;j++)
{
    for(inti=V;i>=bone[j].volume;i--)
    {
       if(bag[i-bone[j].volume]!=0)      
        //如果当前的背包为空的话,就没有必要进行替换骨头
           bag[i]=bag[i-bone[j].volume]+bone[j].value>bag[i]
           ?bag[i-bone[j].volume]+bone[j].value:bag[i];  
           //和上面的--------(1)相同
    }
   bag[bone[j].volume]=(bone[j].value>bag[bone[j].volume])
   ?bone[j].value:bag[bone[j].volume]; 
   //如果没有执行上一个循环,背包为空,就此执行这一步
}

0 0