zoukankan      html  css  js  c++  java
  • 欧拉函数

    View Code
     1 #include<stdio.h>
     2 int Eular(int  n)
     3 {
     4      int i;
     5      int  ans=n;
     6      for(i=2;i*i<=n;++i)
     7      {
     8           if(n%i==0)      //如果i和n不互质,i的倍数全都与n不互质
     9           {
    10                 ans-=ans/i;     //排除掉i的倍数
    11                 while(n%i==0)
    12 n=n/i;       //去掉n中含有的所有i因子
    13                 if(n==1)          // n=1 所有因子排除完毕
    14 break;
    15           }
    16   
    17      }
    18      if(n!=1)        //n!=1  此时的n为素数
    19  ans-=ans/n;
    20      return ans;
    21 }
    22 main()
    23 {
    24      int m;
    25      while(scanf("%d",&m)!=EOF,m)
    26         printf("%d\n",Eular(m));
    27 }  
    View Code
     1 int Eular(int  n)
     2 {
     3      int i;
     4      int  ans=n;
     5      for(i=2;i*i<=n;++i)
     6      {
     7           if(n%i==0)      //如果i和n不互质,i的倍数全都与n不互质
     8           {
     9                 ans-=ans/i;     //排除掉i的倍数
    10                 while(n%i==0)
    11                     n=n/i;       //去掉n中含有的所有i因子
    12                 if(n==1)          // n=1 所有因子排除完毕
    13                     break;
    14           }
    15           
    16      }
    17      if(n!=1)        //n!=1  此时的n为素数
    18          ans-=ans/n;
    19      return ans;
    20 }

     1、以基数1为递增的欧拉函数值,将目标初始化,处理不能被2和3的数。
    2、当以底数为2,基数2(即能被2整除的数)为递增的欧拉函数值。因为将i,以基数2分成i/2段可知,每一段的数从段的开始到段的结束前一个都是互质数。最后一段等于前面所有段的和。
    3、当以底数为3,基数2,为递增的欧拉函数值,即处理的是能被3整除的数。
        3-1、判断是否没被第二种处理
               3-1-1、如果被第二种情况处理的就不能做底数。
               3-1-2、如果未被第二种处理则以此时的情况作底数,以保证,前面每一段里的互质数也能够和后面的数互质。此时,i被分为i/3段,每一段进行整理,以i值做基数进行划分处理,此时i值为phi[i]了,所以可以求得phi[i]可以分为phi[i]/i段,然后每一段有i-1个数是满足互质的。那么总的数和就为phi[i]/i*(i-1)
    可得算法:
    for(i=0;i<=maxn;i++)
         phi[i]=i;
        for(i=2;i<=maxn;i+=2)
          phi[i]/=2;
         for(i=3;i<=maxn;i+=2)
           if(phi[i]==i)
             for(j=i;j<maxn;j+=i)
                 phi[j]=phi[j]/i*(i-1);

  • 相关阅读:
    数据库基础知识复习-2013.09.24
    2013.9.24 答题
    使用单向循环链表实现约瑟夫问题
    C++关于数字逆序输出的两种思路,及字符串逆序输出
    题目要求:建立一个类Str,将一个正整数转换成相应的字符串,例如整数3456转换为字符串"3456".
    将博客搬至CSDN
    Android 下载模块分析(DownloadManager和DownloadProvider)
    linux shell基础语法
    Android过滤Logcat输出
    (Java 多线程系列)Java 线程池(Executor)
  • 原文地址:https://www.cnblogs.com/1114250779boke/p/2643064.html
Copyright © 2011-2022 走看看