UVA-12558 Egyptian Fractions (HARD version) (IDA* 或 迭代加深搜索)
题目大意:经典的埃及分数问题。
代码如下:
# include<iostream>
# include<cstdio>
# include<cstring>
# include<algorithm>
using namespace std;
# define LL long long
int num[5],a,b,k;
LL ans[10000],v[10000];
LL gcd(LL a,LL b)
{
return (b==0)?a:gcd(b,a%b);
}
int get_first(LL a,LL b)
{
return b/a+1;
}
bool judge(int val)
{
for(int i=0;i<k;++i)
if(val==num[i])
return false;
return true;
}
bool better(int d)
{
for(int i=d;i>=0;--i)
if(ans[i]!=v[i])
return ans[i]==-1||v[i]<ans[i];
return false;
}
bool dfs(int cur,int maxd,int from,LL aa,LL bb)
{
if(cur==maxd){
if(bb%aa)
return false;
v[cur]=bb/aa;
if(!judge(v[cur]))
return false;
if(better(cur)){
for(int i=0;i<=cur;++i)
ans[i]=v[i];
}
return true;
}
bool ok=false;
from=max(from,get_first(aa,bb));
for(int i=from;;++i){
while(!judge(i))
++i;
if(bb*(maxd-cur+1)<=i*aa)
break;
v[cur]=i;
LL b2=bb*i;
LL a2=aa*i-bb;
LL g=gcd(a2,b2);
if(dfs(cur+1,maxd,i+1,a2/g,b2/g))
ok=true;
}
return ok;
}
void solve()
{
for(int maxd=1;;++maxd){
memset(ans,-1,sizeof(ans));
if(dfs(0,maxd,get_first(a,b),a,b)){
printf("%d/%d=",a,b);
for(int i=0;i<=maxd;++i)
printf("1/%lld%c",ans[i],(i==maxd)?'\n':'+');
break;
}
}
}
int main()
{
int T,cas=0;
scanf("%d",&T);
while(T--)
{
scanf("%d%d%d",&a,&b,&k);
for(int i=0;i<k;++i)
scanf("%d",num+i);
printf("Case %d: ",++cas);
solve();
}
return 0;
}


浙公网安备 33010602011771号