原题解链接:https://ac.nowcoder.com/discuss/150263
时间复杂度预处理
单次查询
弗洛伊德处理对之间的转换最短路。
先特判与是否相等,相等就是,如果和不相等并且大于等于的话,就是无解。
如果小于,小于,直接查询弗洛伊德表。
如果大于等于的话我们要先使用和将变换一步,然后A的值就小于了,然后查弗洛伊德表,两者里选取优的方案。
#include<cstdio>
#include<cmath>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<bits/stdc++.h>
#include<vector>
using namespace std;
int f(long long x)
{
x%=233;
return (x*x*x+x*x)%233;
}
int g(long long x)
{
x%=233;
return (x*x*x-x*x)%233;
}
int dp[240][240];
int main()
{
for(int i=0;i<233;i++)
{
for(int j=0;j<233;j++)
{
dp[i][j]=0x3f3f3f;
}
dp[i][f(i)]=1;
dp[i][g(i)]=1;
dp[i][i]=0;
}
for(int i=0;i<233;i++)
{
for(int j=0;j<233;j++)
{
for(int k=0;k<233;k++)
{
if(dp[j][k]>dp[j][i]+dp[i][k]) dp[j][k]=dp[j][i]+dp[i][k];
}
}
}
int T;
while(scanf("%d",&T)!=EOF)
{
while(T--)
{
long long a,b;
scanf("%lld %lld",&a,&b);
if(a==b) printf("0\n");
else
{
if(b>=233) printf("-1\n");
else
{
if(min(dp[f(a)][b],dp[g(a)][b])==0x3f3f3f) printf("-1\n");
else printf("%d\n",min(dp[f(a)][b],dp[g(a)][b])+1);
}
}
}
}
}