动态规划之01背包问题

来源:互联网 发布:java权限管理表设计 编辑:程序博客网 时间:2024/06/05 10:35

摘自《背包九讲》 中 基础01背包问题,因为第一次写博客,所以肯定会存在很多问题,因此,还请各位大佬帮我看哈啊,感谢!。。。

原问题描述:有一个容量为v的背包,往里面装入物品,不同的物品体积不同,所具有的价值也不同,求能装入的最大价值。注意:所有物品均不能拆分。

例如: 第i件物品的体积为weight[i],价值为value[i];

解题思路:将问题转化为求解从前i件物品选若干物品放入容量为v的背包中,所能得到的最大价值。

因此,需要考虑的问题为第i件物品,放还是不放。

其状态转移方程为:f[i][v]=max(f[i-1][v],f[i-1][v-weight[i]+value[i]);

方程说明:f[i][v]表示在前i件物品放到一个容量为v的背包中可以获得最大价值。

f[i-1][v]表示在不放入第i件物品时,该背包中所能得到的最大价值。

f[i-1][v-weight[i]+value[i]]表示在背包出去放入第i件物品时的空间所能得到的最大价值,

再加上放入第i件商品所能的到的最大价值,最后的结果即为考虑第i件物品后该背包所

能得到的最大价值。

设背包容量为v,第i件物品体积为weight[i],价值为value[i]。

初始化值:   背包容量v=5; 物品数量为4; 对应的物品体积用数组表示为int[] weight={0,2,3,4,1};  对应价值为int[] value={0,5,10,13,4};

方程为:f[i][v]=max(f[i-1][v],f[i-1][v-weight[i]+value[i]);

图解:   横向为背包容量(j  0~5),纵向为第i件物品(i  0~4)。i\j0123450000000100555520010101015300101013134041011317
子问题:将第i件物品放入容量为j的背包中时,放与不放,对于该背包所能的到的最大价值。

      将前i件物品放入容量为j的背包中,所得到的最大价值。

图解:当i为0时,也就是第0件商品,体积为weight[0]=0,价值为value[0]=0;

    所以将第0件商品商品放入容量为0的背包时,所能得到的价值为0,同理,放入到此行的其它背包中所能得到的价值也为0;

     当i为1时,也就是第1件商品,体积为weight[1]=2,价值为value[1]=5;

   因为这件商品体积为2,因此只能放入容量不小于2的背包中。

           用状态转移方程进行判断:       f[i][v]=max(f[i-1][v],f[i-1][v-weight[i]+value[i]);

           此时f[i][v]代表在图中第i件商品放入容量为v的背包中,所得到的最大价值。

              f[i-1][v]代表在图中在不放入第i件商品时容量为v的背包中,所得到的最大价值(即为第i-1件商品放入容量为v的背包中所得到的最大价值)。

           例如;将此第1件商品放入容量为2的背包中时,有 f[1][2]=max(f[1-1][2],f[1-1][2-weight[1]]+value[1]);

    即:f[1][2]=max(f[0][2],f[0][0]+5);

           此时f[1][2]表示在前1件商品放入容量为2的背包中,得到的最大价值。

            f[0][2]表示在不放入第1件商品到容量为2的背包时,该背包所能得到的价值,

            f[0][0]+5表示在在除去放入第1件物品的空间后,该背包所得到的价值,再加上放入第i件物品后所得到的价值,

  两者加在一起,即为放入第1件商品后所得到的该背包的价值。

          再利用函数max(x,y)即可计较的最后在该位置所能到的的最大价值。

           因此,可以计算出i=1在不同背包中所能得到的最大价值。

          当 i=2, 体积weight[2]=3,价值value[2]=10;

         同上面放入第1件物品一样,该物品只能放入到容量不小于3的背包中,

        因此在将第2件物品放入容量为3的背包中时

       同理用状态转移方程有:   f[2][3]=max(f[1][3]+f[1][0]+value[2]);

      即为:f[2][3]=max(2,10)   f[2][3]=10;

      所以前2件物品在容量为3的背包中,所能得到的最大价值为10;

      因此,计算出剩余物品在不同容量中所能到的最大价值。

     最后得到想要的结果,前4件商品放入容量为5的背包中所能得到的最大价值为:f[4][5]=max(f[3][5],f[3][5-1]+4)=max(13,13+4)=17;

     最后得到:f[4][5]=17;

    因此前i件商品放入容量为4的背包中,所能得到的最大价值为17;


package com.zuxia.pack;public class by01pack {/** * @param args */public static void main(String[] args) {// TODO Auto-generated method stub         int v=5;          //背包容量体积         int number=4;      //物体个数         int[] weight={0,2,3,4,1};  //物品体积         int[] value={0,5,10,13,4};    //物品weight[i]对应的价值value[i];    int getvalue= getValue(v, number, weight, value); System.out.println("前"+number+"件物品放入容量为"+v+"的背包中所能得到的最大价值为:\t"+getvalue);}public static int getValue(int v,int number,int[] weight,int[] value){int f[][]=new int[number+1][v+1]; for(int i=1;i<=number;i++)  //枚举物品 { for(int j=0;j<=v;j++)   //枚举背包容量 { if(j>=weight[i]) { f[i][j]=max(f[i-1][j],f[i-1][j-weight[i]]+value[i]); } } } return f[number][v];}public static int max(int x,int y){        return x>y?x:y;}}



 


原创粉丝点击