C语言回溯法 0-1背包问题
参数说明: c 背包容量 n 物品数 cw 当前背包重量 cp 当前背包价值 bestp 当前最优价值 w[i] 表示物品i的重量 p[i] 表示物品i的价值。 Remind:数据处理前请将所有物品按照单位重量的价值排序,即p[i]/w[i]>=p[i+1]/w[i+1],i=1,2,..n-1。 void BackTrace(int i) { if(i>n)//已经到达叶子 { bestp=cp; return; } if(cw+w[i]<=c) //进入左子树 { cw+=w[i]; cp+=p[i]; BackTrace(i+1); cw-=w[i]; cp-=p[i]; } if(Bound(i+1)>bestp) //当右枝上界大于当前最优价值,才去遍历右枝。否则剪枝。 { BackTrace(i+1); } } int Bound(i)//指当前节点下效益上界(包括其祖先节点到该节点的路径效益和该节点往后代路径的效益) { int cleft=c-cw;//背包剩余可装重量 int total=cp; while(i<n&&w[i]<=cleft) { cleft-=w[i]; total+=p[i]; i++; } if(i<=n) //如果物品i没有放入,则放入物品i的部分,把背包载重量达到满负荷 { total+=cleft*p[i]/w[i]; } return b; }