ArcTan

dfs
随笔 - 16, 文章 - 117, 评论 - 6, 引用 - 0
数据加载中……

欧拉函数(资料+模板)

http://zh.wikipedia.org/wiki/%E6%AC%A7%E6%8B%89%E5%87%BD%E6%95%B0
欧拉函数 :

欧拉函数是数论中很重要的一个函数,欧拉函数是指:对于一个正整数 n ,小于 n 且和 n 互质的正整数(包括 1)的个数,记作 φ(n) 。

完全余数集合:
定义小于 n 且和 n 互质的数构成的集合为 Zn ,称呼这个集合为 n 的完全余数集合。 显然 |Zn| =φ(n) 。

有关性质:
对于素数 p ,φ(p) = p -1 。
对于两个不同素数 p, q ,它们的乘积 n = p * q 满足 φ(n) = (p -1) * (q -1)  。
这是因为 Zn = {1, 2, 3,  ... , n - 1} - {p, 2p, ... , (q - 1) * p} - {q, 2q, ... , (p - 1) * q} , 则 φ(n) = (n - 1) - (q - 1) - (p - 1) = (p -1) * (q -1)  =φ(p) * φ(q)

欧拉定理 :
对于互质的正整数 a 和 n ,有 aφ(n)  ≡ 1 mod n  。
证明:
( 1 ) 令 Zn = {x1, x2, ..., xφ(n)} S = {a * x1 mod n, a * x2 mod n, ... , a * xφ(n) mod n}
        则 Zn = S 。
        ① 因为 a 与 n 互质, xi (1 ≤ i ≤ φ(n)) 与 n 互质, 所以 a * xi  与 n 互质,所以 a * xi  mod n ∈ Zn 。
        ② 若 i ≠ j , 那么 xixj,且由 a, n互质可得 a * xi mod n ≠ a * xj mod n (消去律)。

( 2 )     aφ(n) * x1 * x2 *... * xφ(n) mod n
     
(a * x1) * (a * x2) * ... * (a * xφ(n)) mod n
      
(a * x1 mod n) * (a * x2 mod n) * ... * (a * xφ(n) mod n) mod n
     
  x1 * x2 * ... * xφ(n) mod n
      对比等式的左右两端,因为
xi  (1 ≤ i ≤ φ(n)) 与 n 互质,所以 aφ(n)  ≡  1 mod n (消去律)。
注:
消去律:如果 gcd(c,p) = 1 ,则 ac ≡ bc mod p ⇒ a ≡ b mod p 。

费马定理 :
若正整数 a 与素数 p 互质,则有 ap - 1 ≡ 1 mod p


这个是欧拉定理的特殊情况,p是素数,则p的欧拉函数就是p-1.

补充:欧拉函数公式

( 1 ) pk 的欧拉函数

对于给定的一个素数 p , φ(p) = p -1。则对于正整数 n = pk

 φ(n) = pk - pk -1

证明:
小于 pk 的正整数个数为 pk - 1个,其中
和 pk 不互质的正整数有{p * 1,p * 2,...,p * (pk - 1-1)} 共计 pk - 1 - 1
所以 φ(n) = pk - 1 - (pk - 1 - 1) = pk - pk - 1

( 2 ) p * q 的欧拉函数

假设 p, q是两个互质的正整数,则 p * q 的欧拉函数为

φ(p * q) = φ(p) * φ(q) , gcd(p, q) = 1 。

证明:
令 n = p * q , gcd(p,q) = 1
根据中国余数定理,有
Zn 和 Zp × Zq 之间存在一一映射
(我的想法是: a
∈ Zp , b ∈ Zq ⇔ b * p + a * q ∈ Zn 。
所以 n 的完全余数集合的元素个数等于集合 Zp × Zq 的元素个数。
而后者的元素个数为 φ(p) * φ(q) ,所以有
φ(p * q) = φ(p) * φ(q) 。

( 3 ) 任意正整数的欧拉函数

任意一个整数 n 都可以表示为其素因子的乘积为:

      I
n = ∏ piki (I 为 n 的素因子的个数)
i=1

根据前面两个结论,很容易得出它的欧拉函数为:


I I
Φ(n) = ∏ piki -1(pi -1) = n
(1 - 1 / pi)
i=1
i=1

对于任意 n > 2,2 | Φ(n) ,因为必存在  pi -1 是偶数。


转自:http://blog.csdn.net/hillgong/article/details/4214327

以下程序在http://acm.hrbeu.edu.cn/index.php?act=problem&id=1001&cid=25测试通过:

Compile Error 一次 WA两次 AC:3Ms
总结:代码要写得快,熟练。一定要注意注意越界溢出啊啊啊啊!!!
#include<stdio.h>
#include
<string.h>
#include
<math.h>
#define inf 50000
int prime[10005],b[51005],tot;
int get_prime()
{
    
int i,j;
    memset(b,
0,sizeof(b));
    tot
=0;
    i
=2;
    
while (i<inf)
    
{
        
while (b[i])    i++;
        prime[
++tot]=i;
        j
=i;
        
while (j<inf)
        
{
            b[j]
=1;
            j
+=i;
        }

    }

    tot
--;
}


int main()
{
    
int i,j,k,p,n,m;
    
long long ans;    //这里之前溢出 wa 2次!
    get_prime();
    
while (scanf("%d",&n)==1&&n)
    
{
        ans
=m=n;
        i
=1;
        
while (i<=tot)
        
{
            
if (n%prime[i]==0)
            
{
                ans
=ans*(prime[i]-1)/prime[i];
                
while (n%prime[i]==0)
                    n
=n/prime[i];
            }

            i
++;
        }

        
if (n>prime[tot])
            ans
=ans*(n-1)/n;
        printf(
"%lld\n",ans);
    }

    
return 0;
}



做了好几天数论了,好不容易AC一个题目!!啊啊啊啊

posted on 2012-04-21 17:28 wangs 阅读(418) 评论(1)  编辑 收藏 引用 所属分类: ACM-数学


只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理