动态规划转移方程(二)

7. 完全背包问题

     有N种物品和一个容量为V的背包,每种物品都有无限件可用。第i种物品的体积是v[i],价值是c[i].求解将哪些物品装入背包,可是这些物品的费用总和 不超过背包容量,且价值总和最大。

      这个时候对于每件物品就不是放与不放的问题了,而是放0件1件。。。。。。

      我们可以像01背包一样

      dp[i][j]表示容量为j的背包第i件物品是否要再一次放入我们要从0-V顺序循环

       dp[i][j]=max{dp[i-1][j-v[i]]+c[i],dp[i-1][j]}(注意这里和01背包问题一样但求解的过程不同)

      优化后:dp[j]=max{dp[j],dp[j-v[i]]+c[i]};

for(int i=1;i<=n;i++)
{
       for(int j=v[i];j<=v;j++)//注意这里是从v[i]开始到v
     {
       if(j>=v[i])
       dp[j]=max(dp[j],dp[j-v[i]]+c[i]);
      }
}

8. 多重背包问题

     有N种物品和一个容量为V的背包。第I种物品最多 有n[i]件可用,每件费用是c[i],价值是w[i].求解将哪些物品装入背包可使这些物品的费用总和不超过背包容量,且价值最大。

     因为对于第i种物品有n[i]+1种策略:取0件,取1件.........取n[i]件。

     重点:另dp[i][j]表示前i种物品恰放入一个容量为j的背包的最大价值

    状态转移方程:dp[i][j]=max(dp[i-1][v-k*v[i]]+k*c[i]|0<=k<=n[i])         k表示第i种物品放入k件

for(int i=1;i<=n;i++)
{
    for(int j=v;j>=0;j--)
   {
        for(int k=1;k<=n[i];k++)
      {
         if(j>=k*v[i])
         dp[i][j]=max(dp[i-1][v-k*v[i]]+k*c[i]);
       }
   }
}

9. 二维费用的背包问题

    二维费用的背包问题是指:对于每件物品,具有两种不同的费用:选择这件物品必须同时付出这两种代价;对于每种代价都有一个可付出的最大值(背包容量)。问怎样选择物品可以得到最大的价值。设这两种代价分别是代价1和代价2,第i件物品所需的两种代价分别为a[i]和b[i]。两种代价可付出的最大值(两种背包容量)分别为V和U。物品的价值为W[i];

    费用加了一维,只需状态也加一维即可。设f[i][v][u]表示前i件物品付出两种代价分别为v和u时可获得最大值。

    状态转移方程就是:

     f[i][v][u]=max(f[i-1][v][u],f[i-1][v-a[i]][u-b[i]]+w[i])




猜你喜欢

转载自blog.csdn.net/jiuba5/article/details/52131851