UVA 10934 装满水的气球(Dropping water ballons) (DP)
【题意】
给 k 个气球 从1 楼 开始往上 扔, n层高的楼, 假设 一个球 扔到 F楼 如果 气球破了, 说明 硬度不超过 f 失去一个球 和 一次实验;
如果没破 失去一次实验, 硬度超过f 层
现在想 给k 个气球 确定最少的 实验次数, 才能确定气球硬度
【思路】
典型动态规划问题;
从1 层 开始 往上 扔 dp 【I 】【j】 第 i 个球 实验 j 次实验 确定的 楼层 高数;
对于 第 k 层 如果 破了 那么 就 失去一个球, 一次实验 由 dp 【i-1】【j-1】 +1 获得;
如果没破 那么 就 失去一次实验 dp【i】【j-1】;
所以总层数= dp【i】【j】 = dp【i-1】【j-1】 +1 + dp【i】【j-1】;
提前 预处理63 层;
然后 比较 k个求 多少次 可以 > = n
【代码实现】
#include <iostream> #include <bits/stdc++.h> #include <stdio.h> #include <string.h> #define mem(a,b)memset(a,b,sizeof(a)) #define finds(x,b,n) lower_bound(b+1,b+1+n,x)-b #define lson rt<<1,l,mid #define rson rt<<1|1,mid+1,r #define FIN freopen("input.txt","r",stdin) #define FOUT freopen("output.txt","w",stdout) #define FI(n) IO::read(n) #define Be IO::begin() using namespace std; typedef long long ll; const int INF=0x3f3f3f3f; const int MAXN=1e4+5; const int MOD=1e9+7; const int mod=1e9+7; const double esp=1e-6; const double PI=acos(-1); int dir[5][2]={0,1,0,-1,1,0,-1,0}; ll dp[100][100]; void init() { mem(dp,0); for(int i=1;i<=64;i++) { for(int j=1;j<=64;j++) { dp[i][j]=dp[i-1][j-1]+dp[i][j-1]+1; // printf("%lld \n",dp[i][j]); } } } int main() { init(); ll n,k; while(~scanf("%lld %lld",&k,&n),k) { int flag=1; k=min((ll)63,k); for(int i=1;i<=63;i++) { if(dp[k][i]>=n) { printf("%d\n",i); flag=0; break; } } if(flag) printf("More than 63 trials needed.\n"); } return 0; }
13
岂曰无衣?与子同袍。王于兴师,修我戈矛。与子同仇!
岂曰无衣?与子同泽。王于兴师,修我矛戟。与子偕作!
岂曰无衣?与子同裳。王于兴师,修我甲兵。与子偕行!