hdu4574Bombs(枚举+dfs)
来源:互联网 发布:崩坏3矩阵探索buff最新 编辑:程序博客网 时间:2024/05/22 03:07
题目请戳这里
题目大意:给一个区间[A,B],表示有B - A + 1种火药,火药i的威力值为i,现在要用这些火药做炸弹,每次按原料的字典序做炸弹。每个炸弹的威力值是每种原料威力值的乘积。现在给一个区间[L,R]表示炸弹的威力值范围,求第K个炸弹的配方。
题目分析:因为炸弹的威力值是原料威力值的乘积,R不超过10^9,A至少为2,所以极端情况下炸弹至少要30种原料,所以直接搜就可以了。
首先根据给定的2个区间,求出重合的区间,表示只用一种原料能做的炸弹有多少,如果K满足这个范围,直接输出答案。
然后根据[L,R]区间确定所要原料的数量的上下界。然后枚举原料长度,dfs。
主要的剪枝是,当搜到第i中火药的时候,假设剩下的全部用威力值最大的B种火药,如果还不能达到炸弹威力值下界L,退出;假设剩下的全部用威力值最小的A种火药,已经超过炸弹威力值上界R,退出。
不过我加了这个剪枝还是TLE,后来又加了个小剪枝,就是搜到倒数第二层的时候,最后一层的情况直接统计,不用去搜最后一层了。
详情请见代码:
#include <iostream>#include<cstdio>#include<cstring>#include<algorithm>using namespace std;typedef __int64 ll;ll A,B,L,R,K;ll path[400];bool flag;ll pow(ll a,ll b){ ll ret = a; for(int i = 1;i < b;i ++) ret *= a; return ret;}void dfs(ll cur,int deep,int dp,ll po){ if(flag) return; path[dp] = cur; if(dp + 1 == deep)//倒数第二层 { ll ta = L/po; if(L%po) ta ++; ll tb = R/po; ll tmp; if(tb < cur) tmp = 0; else { if(tb <= B) { if(ta < cur) tmp = tb - cur + 1; else tmp = tb - ta + 1; } else { if(ta < cur) tmp = B - cur + 1; else if(ta <= B) tmp = B - ta + 1; else tmp = 0; } } K -= tmp; if(K > 0) return; else K += tmp; } ll i; if(dp == deep) { if(po >= L && po <= R) K --; if(K == 0) { printf("%I64d\n",po); for(i = 1;i < dp;i ++) printf("%I64d ",path[i]); printf("%I64d\n",path[i]); flag = true; } return; } i = L/po; i = i / (pow(B,(deep - dp - 1))); if(i < cur) i = cur; for(;i <= B;i ++) { if(pow(i,(deep - dp)) * po > R) return; dfs(i,deep,dp + 1,po * i); }}int main(){ int t,cas = 0; ll i,j; scanf("%d",&t); while(t --) { scanf("%I64d%I64d%I64d%I64d%I64d",&A,&B,&L,&R,&K); printf("Case #%d: ",++cas); int cros = 0; if(R < A) { printf("-1\n"); continue; } ll tans; if(R <= B) { if(L < A) { cros = R - A + 1; if(cros >= K) tans = A + K - 1; } else { cros = R - L + 1; if(cros >= K) tans = L + K - 1; } } else { if(L < A) { cros = B - A + 1; if(cros >= K) tans = A + K - 1; } else if(L >= A && L <= B) { cros = B - L + 1; if(cros >= K) tans = L + K - 1; } else cros = 0; } if(cros >= K) { printf("%I64d\n%I64d\n",tans,tans); continue; } K -= cros; ll l,r; l = r = 2; ll ta,tb; ta = A; tb = B; while((ta*A) < R) { r ++; ta = ta * A; } while((B*tb) < L) { l ++; tb = tb * B; } flag = false; for(i = l;i <= r && !flag;i ++) { j = L / (pow(B,i - 1)); if(j < A) j = A; for(;j <= B && !flag;j ++) { if(pow(j,i) > R) break; dfs(j,i,1,j); } } if(!flag) printf("-1\n"); } return 0;}/*1002 2 1 4 12 5 1 4 473 23642 12 20903 294012 50 1 1000000000 8151802 1000000 2 1000000000 10000002 100000 2 1000000000 10000002 10000 2 1000000000 10000002 1000 2 1000000000 10000002 100 2 1000000000 10000002 100000 1000000 1000000000 1000000*//*ans:2242 2-1592004 4 5 20 3742 261611 56510151101 5051273 3 36797287 17 68 84304624631 98266*/
- hdu4574Bombs(枚举+dfs)
- DFS 枚举
- poj2965(枚举||dfs)
- hdu 2208 DFS枚举
- hdu 4152 dfs 枚举
- HDU1045-枚举+DFS
- poj 2965 dfs+枚举
- hdu4739(DFS+枚举)
- 枚举+dfs浅尝
- poj1681 高斯消元+dfs枚举
- poj1753(dfs暴力枚举)
- poj2965(dfs暴力枚举)
- DFS之枚举排列组合
- hdoj 5024 枚举+dfs
- poj 1562 DFS+枚举
- poj2965 DFS暴力枚举
- poj1010 dfs/枚举
- HDU2209+POJ3279 枚举+dfs
- 谈谈Objective-C的警告
- 把自动机用作 Key-Value 存储
- pku 1077 Eight BFS
- Redhat6.3安装matlab找不到libXP.so.6解决方法
- PythonChallenge 挑战之路 Level-31
- hdu4574Bombs(枚举+dfs)
- Uninstall Bitdefender Antivirus Free Edition with WindowsUninstaller.Org Removal Tips
- C#生成pfx用户数字证书
- URLRewriter
- visual studio 常用快捷键
- flex 弹出框Alert
- Burp suite 暴力破解shell密码详细教程
- C++, C#引用的区别和C#的类为什么没有拷贝构造函数
- WinDriver简介(或介绍)