【数论】GCD

F. GCD-GCD-GCD [ Problem 4045 ]

Description

给你两个数a,m;
问你在 [0,m − 1] 范围内有几个数 x 满足gcd(a,m) = gcd(a + x,m);

Input

第一行一个整数T;
接下来T行,每行两个整数a,m;
1 ≤ a < m ≤ 1e9

Output

针对每两个数,输出满足条件的x的数量。

Samples
Input Copy

3
4 9
5 10
42 9999999967

Output

6
1
9999999966

Hint

对于第一个4 9:
满足的x是:0 1 3 4 6 7

解题思路:
由更项减损术求最大公约数可知,若 x > y , 则 有 g c d ( x , y ) = g c d ( x − y , y ) x>y,则有gcd(x,y)=gcd(x-y,y) x>y,gcd(x,y)=gcd(xy,y)
g c d ( a + x , m ) = g c d ( a , m ) = G c d ; gcd(a+x,m)=gcd(a,m)=Gcd; gcd(a+x,m)=gcd(a,m)=Gcd;
g c d ( a + x G c d , m G c d ) = 1 gcd(\frac{a+x}{Gcd},\frac{m}{Gcd})=1 gcd(Gcda+x,Gcdm)=1
当 a + x < m 时 , 即 求 [ a G c d , m G c d ) 中 与 m G c d 互 质 的 个 数 ; 当a+x < m时,即求[\frac{a}{Gcd},\frac{m}{Gcd})中与\frac{m}{Gcd}互质的个数; a+x<m[Gcda,Gcdm)Gcdm
当 a + x ≥ m 时 , 有 更 项 减 损 术 可 得 , g c d ( a + x G c d − m G c d , m G c d ) = 1 , 当a+x \geq m时,有更项减损术可得,gcd(\frac{a+x}{Gcd}-\frac{m}{Gcd},\frac{m}{Gcd})=1, a+xmgcd(Gcda+xGcdm,Gcdm)=1,
即 求 [ 0 , a G c d ) 中 与 m G c d 互 质 的 个 数 ; 即求[0,\frac{a}{Gcd})中与\frac{m}{Gcd}互质的个数; [0,GcdaGcdm

取上述两种情况的并集可将该题转化为:求 m G c d \frac{m}{Gcd} Gcdm 的欧拉函数即可。
【数论】GCD_第1张图片

上代码:

#pragma GCC optimize(2)
#pragma G++ optimize(2)
#include
using namespace std;
typedef long long ll;
ll get_oula(ll n)
{
     
	ll ans = n;
	for(int i=2;i<=n/i;i++)
    {
     
        if(n%i==0) ans=ans/i*(i-1);
        while(n%i==0) n/=i;
    }
    if(n>1) ans=ans/n*(n-1);
    return ans;
}
int main()
{
     
	int t;
	scanf("%d",&t);
	while(t--)
	{
     
		ll a,m;
		scanf("%lld%lld",&a,&m);
		ll gcd = __gcd(a,m);
		ll ans=get_oula(m/gcd);
		cout << ans << endl;
	} 
	return 0;
 }

你可能感兴趣的:(【数论】GCD)