2022“杭电杯”中国大学生算法设计超级联赛(3)1002/1011补题
2022“杭电杯”中国大学生算法设计超级联赛(3)
大量参考官方题解
1002 Boss Rush
题意:给定个技能,每个技能最多使用一次,释放第个技能需要的回合数为,伤害持续的回合为,持续回合的伤害为。在一个技能释放时不能释放其他技能,问伤害达到需要的回合数至少为多少。
思路:发现很大,考虑二分答案 。二分答案需要求出给定的回合内能造成的最大伤害,暴力算的复杂度是阶乘,肯定T。但是发现很小,可以二进制枚举已经释放过的技能,设这个集合为,定义为当前集合在给定回合内能够造成的最大伤害,枚举不在当前集合的技能作为下一个技能进行状态转移
状态转移:
AC代码:
时间复杂度
#include<bits/stdc++.h> using namespace std; #define rep(i, a, b) for(int i = (int)(a); i <= (int)(b); i ++) #define IO ios::sync_with_stdio(false);cin.tie(0);cout.tie(0); typedef long long LL; const int N = 20, M = 1e5 + 10; int n,dd[20]; LL H,f[1<<N]; struct WEAPON{ int k,m; LL dmg[M]; }wp[N]; void init(){ dd[0]=1; rep(i,1,20) dd[i]=dd[i-1]<<1; } bool check(int rd){ rep(i,0,(1<<n)-1) f[i]=-1; f[0]=0; for(int j=0;j < 1<<n;j++){ if(f[j]==-1) continue; LL cur_w=0; rep(k,0,n-1) if(j>>k&1) cur_w+=wp[k].k; rep(k,0,n-1){ if(j>>k&1) continue; if(rd-cur_w>0){ int t=rd-cur_w; f[j+dd[k]]=max(f[j+dd[k]],f[j]+wp[k].dmg[min(wp[k].m,t)]); if(f[j+dd[k]]>=H) return true; } } } return false; } void work() { cin>>n>>H; int sum=0; rep(i,0,n-1) rep(j,0,M-1) wp[i].dmg[j]=0; rep(i,0,n-1){ cin>>wp[i].k>>wp[i].m; sum+=max(wp[i].k,wp[i].m); rep(j,1,wp[i].m){ LL t; cin>>t; wp[i].dmg[j]=wp[i].dmg[j-1]+t; } } int l=1,r=sum+1; while(l<r){ int mid=l+r>>1; if(check(mid)) r=mid; else l=mid+1; } cout<<(l==sum+1?-1:l-1)<<endl; } signed main() { IO init(); int test=1; cin >> test; while (test--) work(); return 0; }
1011 Taxi
题意:给定个点,第个点的坐标为 ,权值为 ,有个询问,每个询问给定一个点,坐标为,求
思路:如果没有的限制,那么是经典问题。根据,有
可以发现只要分别记录的最大值就可以在时间内求出所有点到的曼哈顿距离的最大值。
接下来的步骤是把个点以从小到大排序,维护上述四个值的后缀最大值然后二分区间,推荐看官方题解十分详细
AC代码:
时间复杂度
#include<bits/stdc++.h> using namespace std; #define rep(i, a, b) for(int i = (int)(a); i <= (int)(b); i ++) #define rrep(i, a, b) for(int i = (int)(a); i >= (int)(b); i --) #define IO ios::sync_with_stdio(false);cin.tie(0);cout.tie(0); const int N = 1e5 + 10; struct Point{ int X,Y,W; }p[N]; int a[N],b[N],c[N],d[N]; bool cmp(Point &x,Point &y){ return x.W<y.W; } void work() { int n,q; cin>>n>>q; rep(i,1,n) cin>>p[i].X>>p[i].Y>>p[i].W; sort(p+1,p+n+1,cmp); a[n+1]=-INF,b[n+1]=-INF,c[n+1]=-INF,d[n+1]=-INF; rrep(i,n,1){ a[i]=max(p[i].X+p[i].Y,a[i+1]); b[i]=max(p[i].X-p[i].Y,b[i+1]); c[i]=max(-p[i].X+p[i].Y,c[i+1]); d[i]=max(-p[i].X-p[i].Y,d[i+1]); } while(q--){ int x,y; cin>>x>>y; int l=1,r=n,ans=0; while(l<=r){ int mid=l+r>>1; int cur_w=p[mid].W; int cur_d=-x-y+a[mid]; cur_d=max(cur_d,-x+y+b[mid]); cur_d=max(cur_d,x-y+c[mid]); cur_d=max(cur_d,x+y+d[mid]); if(cur_w<=cur_d){ ans=max(ans,cur_w); l=mid+1; } else{ ans=max(ans,cur_d); r=mid-1; } } cout<<ans<<endl; } } signed main() { IO int test=1; cin >> test; while (test--) work(); return 0; }
能力有限欢迎勘误
本文作者:xhy666
本文链接:https://www.cnblogs.com/xhy666/p/16523221.html
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· 从HTTP原因短语缺失研究HTTP/2和HTTP/3的设计差异
· 三行代码完成国际化适配,妙~啊~