SCU 3547 Coprime(容斥)

来源:互联网 发布:unity3d建筑可视化 编辑:程序博客网 时间:2024/06/09 20:04

Description

Please write a program to calculate the k-th positive integer that is coprimewith m and n simultaneously. A is coprime with B when their greatest commondivisor is 1.

Input

The first line contains one integer T representing the number of test cases.For each case, there's one line containing three integers m, n and k (0 < m, n, k<= 10^9).

Output

For each test case, in one line print the case number and the k-th positiveinteger that is coprime with m and n.Please follow the format of the sample output.

Sample Input

36 9 16 9 26 9 3

Sample Output

Case 1: 1Case 2: 5Case 3: 7

Hint

分析:直接二分搞一下。由于同时和n,m互质,那么这个数一定不能存在n或m的素因子

#include<cstdio>#include<cstring>#include<algorithm>#include<vector>#include<string>#include<iostream>#include<queue>#include<cmath>#include<map>#include<stack>#include<set>using namespace std;#define REPF( i , a , b ) for ( int i = a ; i <= b ; ++ i )#define REP( i , n ) for ( int i = 0 ; i < n ; ++ i )#define CLEAR( a , x ) memset ( a , x , sizeof a )const int INF=0x3f3f3f3f;typedef long long LL;int t,n,m,k;int fac[100],tot;void solve(int x){    for(int i=2;1LL*i*i<=x;i++)    {        if(x%i==0)        {            while(x%i==0)                x/=i;            fac[tot++]=i;        }    }    if(x>1)        fac[tot++]=x;}LL ok(LL x){    int status=(1<<tot);    LL sum=0;    for(int i=1;i<status;i++)    {        LL s=1,cnt=0;        for(int j=0;j<tot;j++)        {            if(i&(1LL<<j))            {                s*=fac[j];                cnt++;            }        }        if(cnt&1)            sum+=x/s;        else            sum-=x/s;    }    return x-sum;}int main(){    int cas=1;    scanf("%d",&t);    while(t--)    {        scanf("%d%d%d",&n,&m,&k);        tot=0;        solve(n);        solve(m);        sort(fac,fac+tot);        tot=unique(fac,fac+tot)-fac;        LL l=1,r=1e12;        while(l<=r)        {            LL mid=(l+r)>>1;            if(ok(mid)>=k)                r=mid-1;            else                l=mid+1;        }        printf("Case %d: %lld\n",cas++,l);    }    return 0;}


0 0
原创粉丝点击