poj3358

  • #include<iostream>
    #include<cstdlib>
    #include<cstdio>
    using namespace std;
    typedef long long LL;
    
    
    LL pow(LL a,LL p,LL m){
    	LL d=1,t=a;
    	while(p>0){
    	   if(p&1==1){
       		  d=(d*t)%m;
       	   }
       	   t=(t*t)%m;
       	   p=p>>1;
    	}
    	return d;
    }
    
    int  enlerFun(int n){
    	int count = n;
        for(int i=2;i<=n;i++){
          if(n%i==0){
          	 count=count-count/i;
          	 while(n%i==0){n=n/i;}
           }  	
         }	
        return count;	
    }
    
    LL gcd(LL a,LL b){
    	 return b==0?a : gcd(b,a%b);
    }
    
    int main()
    {  
        int t=0;
        LL p,q,d,time,yue,minyue; //minyue最小的能使公式成立的约数 
        while( ~ scanf("%I64d/%I64d",&p,&q)  ){       
         d=gcd(p,q);p/=d;q/=d;  //化简分子和分母  
         //printf("%I64d %I64d",p,q);  
         time=1;
         while( (q&1)==0 ){  //注意添加括弧 
                  time++;
                  q=q>>1;
                 }
         //time就是起始位置3088601  
         yue=enlerFun(q);
         minyue=yue;
         //printf("%d\n",minyue);
         
         
         
         for(int i=1;i*i<=yue;i++){
            if(yue%i==0){
                if(pow(2,i,q)==1 &&  i<minyue){minyue=i;} //符合公式,大擂台找最小 
                if(pow(2,yue/i,q)==1 &&  (yue/i)<minyue){minyue=(yue/i);}
            }    
             //printf("***%d\n",minyue);
         }
         printf("Case #%d: %d,",++t,time); printf("%d\n",minyue);
        }//while
    	
    	return 0;
    }
    
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值