hdu 5584 gcd/lcm/数学公式

input

T  1<=T<=1000

x y

output

有多少个起点可以走n(n>=0)步走到(x,y),只能从(x,y)走到(x,y+lcm(x,y))/(x+lcm(x,y),y)

标准解:从(x,y0)走到(x,y),则设x=ag,y0=bg,g=gcd(x,y0),有y=bg+abg=(a+1)bg,因为a,b互质,a,(a+1)互质,所以a和(a+1)b互质,所以若可以从(x,y0)走到(x,y),有gcd(x,y0)=gcd(x,y),然后将x和y中gcd(x,y)除去之后不断除以(x+1)即可

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <set>
 4 #include <algorithm>
 5 
 6 using namespace std;
 7 
 8 typedef long long LL;
 9 
10 //求最大公约数
11 LL gcd(LL a, LL b) { if(!b) return a; else return gcd(b,a%b); }
12 
13 int main()
14 {
15     int t,Case = 0;
16     scanf("%d",&t);
17     while(t--)
18     {
19         LL ex,ey; //终点坐标
20 
21         scanf("%lld%lld",&ex,&ey);
22         LL GCD = gcd(ex,ey);
23         ex/=GCD,ey /=GCD;
24         int ans = 0;
25         while(1)
26         {
27             if(ey < ex) swap(ex,ey);
28             ans++;
29             if(ey % (ex+1)) break;
30             ey /= (ex+1);
31         }
32 
33         printf("Case #%d: %d\n",++Case,ans);
34     }
35 }
answer
 1 #include <cstdio>
 2 #include <queue>
 3 #include <cstring>
 4 #include <iostream>
 5 #include <cstdlib>
 6 #include <algorithm>
 7 #include <vector>
 8 #include <map>
 9 #include <set>
10 #include <ctime>
11 #include <cmath>
12 #include <cctype>
13 #define MAX 100000
14 #define LL long long
15 int cas=1,T,x,y,d[1000],dn;
16 void find(int x,int *d,int& dn)
17 {
18     dn=-1;
19     int m=sqrt(x);
20     for(int i=1;i<=m;i++) if(x%i==0) d[++dn]=i;
21     for(int i=dn;i>=0;i--) d[++dn]=x/d[i];
22 }
23 int gcd(int a,int b) { return b==0?a:gcd(b,a%b); }
24 int main()
25 {
26 //    freopen("in","r",stdin);
27     scanf("%d",&T);
28     while(T--)
29     {
30         scanf("%d%d",&x,&y);
31         int step=1,flag=1;
32         while(flag&&x!=y)
33         {
34             flag=0;
35             if(x>y) std::swap(x,y);
36             int g=gcd(x,y);
37             find(g,d,dn);
38             for(int i=dn;i>=0;i--)
39             {
40                 if(y%(d[i]+x)==0)
41                 {
42                     int y1=y/(d[i]+x)*d[i];
43                     if(gcd(x,y1)==d[i]) { y=y1;step++;flag=1;break; }
44                 }
45             }
46         }
47         printf("Case #%d: %d\n",cas++,step);
48     }
49     //printf("time=%.3lf",(double)clock()/CLOCKS_PER_SEC);
50     return 0;
51 } 
My Code

 

posted @ 2015-12-16 14:56  cdongyang  阅读(282)  评论(0编辑  收藏  举报