1. 程式人生 > >hdu 2955 01背包

hdu 2955 01背包

clas -- AC con pre ems pac namespace 不可

題目鏈接:http://acm.hdu.edu.cn/showproblem.php?pid=2955

這題蠻有意思的,首先01背包的狀態轉移這些不說了,很簡單。但關鍵這題該如何建立起01背包的模型那?如果以被抓的概率作為背包容量,由於浮點數,精度是不可靠的。

所以只能以金錢為背包容量,所以所有銀行的總資產,最為背包容量,然後我們以逃跑幾率進行動態轉移。逃跑幾率只要 用 1- p 就好了,關鍵一點由於是算的概率,所以逃跑

幾率是想乘的,大家可以想想,不可能相加。最後我們就能完美寫成代碼了。(還有如果沒搶到,那麽概率為1 ,這也不要忽略了)

AC code:

#include <bits/stdc++.h>
using
namespace std; const int MAX = 10006; /*hdu2955 01背包--這裏我們考慮以金錢為容量*/ int main () { int T,n,t[101]; float p,v[101]; float f[MAX]; cin>>T; while(T--) { cin >> p >> n; p = 1-p;//最低逃生幾率 memset (f,0,sizeof(f)); int sum = 0; for (int i=0
;i<n;++i) { cin>>t[i]>>v[i]; v[i] = 1-v[i];//這樣就變成了逃生幾率,逃生幾率越大越好 sum +=t[i]; } f[0] = 1;//沒搶到錢,逃走概率100% for (int i=0;i<n;++i) for (int j= sum;j>=t[i];--j ) { f[j] = max (f[j],f[j-t[i]]*v[i]);//這裏一定要乘,因為你這是算概率,在前面逃走的概率下。
} int fg = 0; for (int i=sum;i>=0;--i) if (f[i] >= p) { fg = i;break; } cout<<fg<<endl; } return 0; } /* 3 0.04 3 1 0.02 2 0.03 3 0.05 0.06 3 2 0.03 2 0.03 3 0.05 0.10 3 1 0.03 2 0.02 3 0.05 */

hdu 2955 01背包