假设当前数字是114514,我们得到的答案必定是114514abcd
-
枚举扩展位数,由于答案说明在18位以内,故扩展位数最多枚举18次
-
获取扩展后的,例如我们扩展了2位,应该得到11451400
-
寻找第一个大于等于11451400的完全平方数,在二分的时候二分的是
中的
,由于最大答案不会超过18位,因为直接枚举到
即可
-
当这个数减去11451400的结果小于100时(即恰好可以填完00,他前面几个数和没扩展的一样),说明可以构成答案,否则就继续扩展。
总时间复杂度,事实上这个常数非常小,跑了
不到。
#include <iostream>
#include <math.h>
using namespace std;
typedef long long ll;
ll pre[20];
int _log10(ll x){
int ws=0;
while(x){
ws++;
x/=10;
}
return ws;
}
void solve(){
ll x;
cin>>x;
int ws=_log10(x);
for(int i=1;i<=18;i++){ //枚举扩展的位数
if(ws-1+i>18)break; //如果位数扩展超出了18位就不枚举了
ll y=x*pre[i];
ll l=1,r=1e9;
while(l<r){
ll mid=(l+r)>>1;
if(mid*mid >=y)r=mid;
else l=mid+1;
}
if(l*l - y < pre[i]){//例如12345 -12300=45
cout<<l*l<<"\n";
break;
}
}
return;
}
int main(){
ios::sync_with_stdio(false),cin.tie(0);
int T=1;
cin>>T;
pre[0]=1;
for(int i=1;i<=18;i++)pre[i]=pre[i-1]*10;
while(T--)solve();
return 0;
}

京公网安备 11010502036488号