背包小结

来源:互联网 发布:帝国cms图片集模板 编辑:程序博客网 时间:2024/05/16 12:06
int  dp[MAXN], m;   // m : 背包的总容量
(ps    01背包从后往前。完全背包从前往后。
(1)若要求背包必须放满,则初始如下:
        f[0] = 0 , f[1...V]表示-INF。表示当容积为0时,只接受一个容积为0的物品入包。
   (2)若要求背包可以空下,则初始化如下:
        f[0...V] = 0 ,表示任意容积的背包都有一个有效解即为0。

0-1 背包

有N件物品和一个容量为m的背包。第i件物品的费用是c[i],价值是w[i]。求解将哪些物品装入背包可使价值总和最大。

特点:每种物品仅有一件,可以选择放或不放。


//01背包
void zeroOnePack(int weight,int value)
{
for(int i=m;i>=weight;i--)
dp[i]=max(dp[i],dp[i-weight]+value);
}

 

完全背包

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

特点:每种物品都有无限件可用。


//完全背包
void completePack(int weight,int value)
{
for(int i=weight;i<=m;i++)
dp[i]=max(dp[i],dp[i-weight]+value);
}

多重背包

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

特点:第i种物品最多有n[i]件可用。


//多重背包
void multiplePack(int weight,int value,int amount)
{
if(weight*amount>=m)
completePack(weight,value);
else
{
int k=1;
while(k<amount)
{
zeroOnePack(k*weight,k*value);
amount=amount-k;
k<<=1;
}
zeroOnePack(amount*weight,amount*value);
}
}


//01背包
void zeroOnePack(int weight,int value)
{
for(int i=m;i>=weight;i--)
dp[i]=max(dp[i],dp[i-weight]+value);
0 0