该值太长,长度不应超过 100 个字符。
NegetiveEdgeWeight · · 题解
给出一个 申请卡掉打表做法然后升青。
考虑一个很显然的做法:枚举 cbrt 算出 cbrt 的大常数,过不去。
怎么办?我会打表! 打表太邪恶了,考虑优化。
首先你意识到把 那不和打表本质相同吗。
你发现当
得到这个之后怎么办呢,你发现
:::info[更具体的,]
若
有答案
若
| 有答案 |
|---|
那
轻松拿下非打表最优解。那不还是被打表打爆了吗。
:::success[Code]
#include<bits/stdc++.h>
#define int long long
#define For(a,b,c) for(int a=(int)b;a<=(int)(c);a++)
using namespace std;
constexpr int N=5e3+5,MOD=998244353;
int pw[N],ans[205][3],vis[205],x;
void f(int x,int a,int b,int c){
if(x<0||x>200) return;
vis[x]=1,ans[x][0]=a,ans[x][1]=b,ans[x][2]=c;
}
signed main(){
For(i,0,5000)
pw[i]=i*i*i;
For(a,0,5)
For(b,0,5)
For(c,0,5)
f(pw[a]+pw[b]+pw[c],a,b,c);
For(a,0,5000){
int c=a;
For(b,0,a){
int s=pw[a]+pw[b];
while(c<5000&&pw[c+1]<=s) c++;
if(c==5000&&s-pw[c]>200) break;
for(int k=c;k>=0&&s-pw[k]<=200;k--)
f(s-pw[k],a,b,-k);
for(int k=c+1;k<=5000&&pw[k]-s<=200;k++)
f(pw[k]-s,-a,-b,k);
}
}
int t;
cin>>t;
while(t--){
cin>>x;
if(vis[x])
cout<<ans[x][0]<<' '<<ans[x][1]<<' '<<ans[x][2]<<'\n';
else
cout<<"impossible\n";
}
return 0;
}
:::