【日常刷题】最大公约数与最小公倍数问题

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/Ronaldo7_ZYB/article/details/85333988

最大公约数与最小公倍数问题

题面

题目描述

输入2个正整数x0,y0(2≤x0<100000,2≤y0<=1000000),求出满足下列条件的P,Q的个数。
条件:
P,Q是正整数
要求P,Q以x0​为最大公约数,以y0​为最小公倍数.
试求:满足条件的所有可能的2个正整数的个数.

输入格式:

2个正整数x0,y0

输出格式:

1个数,表示求出满足条件的P,Q的个数

输入样例

3 60

输出样例

4

说明

P,Q有4种
1、3,60
2、15,12
3、12,15
4、60,3


题解

显然暴力枚举是不明智的,我们需要数学推导。

这里我们用 x x 代替 x 0 x0 y y 代替 y 0 y0

p = k 1 x , q = k 2 x p=k1*x,q=k2*x .在这里一定满足 p , q p,q 互质,即 g c d ( p , q ) = 1. gcd(p,q)=1.

由于 a b = g c d ( a , b ) l c m ( a , b ) p q = k 1 x k 2 x = x y a*b=gcd(a,b)*lcm(a,b)→p*q=k1*x*k2*x=x*y .

化简,得: k 1 k 2 x = y k 1 k 2 = y / x k1*k2*x=y→k1*k2=y/x .

y % x 0 y\%x≠0 ,显然无解。

我们因此可以在根号的时间内枚举 y / x y/x 的因数 a , b a,b 且满足 g c d ( a , b ) = 1 gcd(a,b)=1 ,说明是一组合法的解;由于顺序可以调换,答案需要 + 2. +2.


C O D E CODE

#include<bits/stdc++.h>
using namespace std;
inline int gcd(int a,int b)
{
    if (b==0) return a;
    else return gcd(b,a%b); 
}
int main()
{
    int a,b,sum=0;
    cin>>a>>b;
    int num=b/a;
    if (b%a!=0) { cout<<0; exit(0); }
    for (int i=2;i*i<=b/a;++i)
    {
        if (num%i!=0) continue;
        if (gcd(i,b/a/i)==1) sum+=2;
    }	
    if (num>1) sum+=2;
    if (sum==0) cout<<0;
    else cout<<sum<<endl;
    return 0;
} 

猜你喜欢

转载自blog.csdn.net/Ronaldo7_ZYB/article/details/85333988