P1602 Sramoc问题 题解
思路很简单
直接爆搜
用bfs更好得到答案,从最高位往低位搜索。
但是时间会爆掉所以需要优化:对于已经搜到的某个数 $x$ ,如果有 $x \equiv y( mod\ n )$ 那么有 $ax+b \equiv ay+b$ 即下一次搜到同余的数就不用再搜索一次可以直接退出了。比如要凑到13的倍数,那么27和40只需要从27开始往下搜,搜到40直接退出即可,因为27肯定是更优的
但是要爆long long。
高精/int128/string 均可。
毒瘤 不做了
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<queue>
using namespace std;
inline int r()
{
int s=0,k=1;char c=getchar();
while(!isdigit(c))
{
if(c=='-')k=-1;
c=getchar();
}
while(isdigit(c))
{
s=s*10+c-'0';
c=getchar();
}
return s*k;
}
int f[1000005],pw[101],n,m,t;
string nn;
int to_mod(string s,int mod)
{
int tmp=0;
int len=s.length();
for(int i=0;i<len;i++)
{
tmp*=10;
tmp+=(s[i]-'0');
tmp%=mod;
}
return tmp;
}
string mto_string(int x)
{
string s;
int len=0;
while(x)
{
len++;
string tmp;
tmp+=(char)(x%10+'0');
s.insert(0,tmp);
x/=10;
}
return s;
}
bool comp(string a,string b)//return a>b?
{
int lena=a.length(),lenb=b.length();
if(lena>lenb)return 1;
else if(lena<lenb)return 0;
else return a>=b;
}
signed main()
{
// freopen("test.in","r",stdin);
// freopen("a.out","w",stdout);
// t=r();
t=1;
pw[0]=1;
for(int i=1;i<=16;i++)
pw[i]=pw[i-1]*10;
for(int i=1;i<=t;i++)
{
m=r();n=r();
nn=mto_string(n);
queue<string>q;
q.push("");
while(!q.empty())
{
string x=q.front();
// cout<<"============================="<<endl;
// cout<<"now:"<<x<<endl;
q.pop();
if(comp(x,nn)&&to_mod(x,n)==0)
{
cout<<x;
break;
}
for(int i=0;i<m;i++)
{
if(i==0&&x=="")continue;
string xx=x+(char)(i+'0');
if(!f[to_mod(xx,n)])
{
// cout<<"push"<<xx<<" "<<to_mod(xx,n)<<endl;
q.push(xx);
if(comp(xx,nn))f[to_mod(xx,n)]=1;
}
}
}
}
}
本文来自博客园,作者:lei_yu,转载请注明原文链接:https://www.cnblogs.com/lytql/p/15017611.html