10.有依赖的背包问题

tech2023-07-15  122

#include<iostream> #include<cstring> #include<algorithm> using namespace std; const int N=103; int n,m; int h[N],v[N],ne[N],e[N],w[N],idx; int f[N][N];//f[i][j]:以i为根的子树,体积不超过j的集合 void add(int a,int b) { e[idx]=b; ne[idx]=h[a]; h[a]=idx++; } void dfs(int u) { for(int i=h[u];i!=-1;i=ne[i])//循环物品 { int son=e[i]; dfs(son); for(int j=m-v[u];j>=0;j--)//循环体积 for(int k=0;k<=j;k++)//循环方案 f[u][j]=max(f[u][j],f[u][j-k]+f[son][k]); //循环方案的时候,没有按每个子树为方案是因为子树的数量可能会达到100,那么可能的方案数就是 //2^100,这在时间和空间上都属不允许的,所以以不同的体积作为不同的方案数,方案的个数就是不同 //体积的个数 } //把根节点的体积加进去 for(int i=m;i>=v[u];i--) f[u][i]=f[u][i-v[u]]+w[u]; //上面求的方案是在不包含u的体积的情况下求得的,也就是说体积比u的体积小的方案是不合法的,只能作为一个 //中间值 for(int i=0;i<v[u];i++) f[u][i]=0; } int main() { cin>>n>>m; memset(h,-1,sizeof h); int root; for(int i=1;i<=n;i++) { int P; cin>>v[i]>>w[i]>>P; add(P,i); if(P==-1) root=i; } dfs(root); cout<<f[root][m]; return 0; }

 

最新回复(0)