一.分組揹包(每組只能選乙個)
所謂分組揹包,就是把物品分成n組,每組裡面m個物品,從這n組中每組選乙個物品,使得在揹包體積是v的條件下價值最大;
思路:對於每一組由於只能選乙個,所以就是決策這一組中選哪乙個獲得的價值最大;
for
(int i=
1;i<=n;i++
)//列舉這是第幾組 ,num[i]代表第i組物品的個數,v[i][j]表示第i組第j個物品的體積,w同理
}
二:混合揹包
混合揹包就是給n個物品,其中一些物品只有乙個,還有一些有有限個,另一些有無限個,求取在揹包體積為v的條件下所能達到的最大價值.
思路:把物品重新進行分類,有限個可以通過二進位制優化為01揹包,乙個就是01揹包,然後標記一下當前物品是要進行01揹包還是完全揹包就完事兒.
int cnt=
0,w[size]
,v[size]
,mark[size]
;//cnt為分堆後物品的個數,v為花費,w為價值,mark標記陣列,標記這個物品進行的種類
for(
int i=
1;i<=n;i++
)else
if(s==1)
//01揹包
else
//多重揹包
if(s)}}
//根據分組進行對應的01揹包和完全揹包 balabalabala
三.有依賴的揹包
簡單來說就是給n個物品,但這n個物品有些之間有依賴關係,比如a和b,如果要選a,就必須選擇b,選擇了b,卻不一定選擇a,在這種條件**積v能達到的最大價值.
思路:曾經碰到的時候一看題解就覺得很複雜,於是暫時放了下,後來在學樹形dp時,又看到這個問題,其實這個本質就是乙個樹形dp;因為這n個物品的關係網就構成了一棵樹,在樹上進行決策。我們假設已經建好了物品之間的關係樹
//模板
void
dfs(
int now,
int pre)
//dp[i][j]代表以i為根結點,最大體積為j時能獲得的最大價值
//更新dp[now];
for(
int i=v;i>=cost[now]
;i--
) dp[now]
[i]=dp[now]
[i-cost[now]
]+val[now]
;//子節點對當前節點的影響都更新完了,應該更新當前節點的狀態,由於於要拿字節點,所以當前節點必須拿
for(
int i=
0;i;i++
) dp[now]
[i]=0;
//拿不了當前物品的,其子節點也不能拿,也就是最大價值是0;
}
用這個方法去寫「金明的預算方案」的時候t了,真是殺雞用了牛刀,因為附件只有0,1,2三種情況,就相當於多了幾種情況的01揹包,在每種情況中取最大就行了
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#define mod (1000000000+7)
#define middle (l+r)>>1
#define size 10000000+10
#define lowbit(x) (x&(-x))
#define lson (rt<<1)
#define rson (rt<<1|1)
typedef
long
long ll;
typedef
long
double lb;
const
int inf_max =
0x3f3f3f3f
;const ll linf =
9e18
;const
int maxn =
100+10;
const
long
double nature =
2.7182818
;const
double eps=
0.0001
;using
namespace std;
int v,n,cost[maxn]
,val[maxn]
,dp[
40000
],fv[maxn][5
],fw[maxn][5
];// 思路:列舉每乙個主件,在每個情況下更新最大值
voiddp(
)}void
initial()
intmain()
else}dp
();printf
("%d\n"
,dp[v]);
}return0;
}
混合揹包 分組揹包
啥是混合揹包呢,就是包含01揹包,完全揹包,多重揹包。有n件物品,揹包承重最大為m,w i 代表重量,v i 代表價值,s i 代表種類。s i 1,可用1次,s i 0,可用無限次,s i 0,可用s i 次.解法 見 const int maxn 1e4 5 int n,m,dp m 1 w n...
通天之分組揹包 分組揹包
本人水平有限,題解不到為處,請多多諒解 本蒟蒻謝謝大家 題目 傳送門 分組揹包的模板 偽 1 for int i 1 i 組數 i 6 7 直接套模板即可。code 1 include2 pragma gcc optimize 3 3const int n 1e5 10 4 using namesp...
有依賴的揹包
關鍵 當遞迴處理u結點的子樹返回時,進行分組揹包的決策,各個子樹中的結點可能非常多,可能有100多個結點,因此,如果以方案來劃分最多有2 100種類別,所以要改用體積來劃分 從j表示當前除去v u 的體積,j從 m v u 0 的體積中列舉 類別 k選取體積是0,是1.是j 選乙個 轉化為分組揹包問...