扩展欧几里德与中国剩余定理1

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

欧拉函数性质
练习
ቤተ መጻሕፍቲ ባይዱ
1:给出一个数n,求出1~n-1中,所有 与n不互质的数之和[与n的最小公约数>1] (MOD 1000000007)。
2.poj 3090

线性同余方程

对于方程 a*x+b*y=c,该方程等价于 ax ≡ c (mod b);有整数解得充分必要 条件是(c %gcd(a,b)==0),这个 定理这里就不证明了,数论书上都有。

所以方程 a*x+b*y=n;我们可以先用扩 展欧几里德算法求出一组x0,y0。也就 是a*x0+b*y0=(a,b);然后两边同时 除以(a,b),再乘以n。这样就得到了 方程a*x0*n/(a,b)+b*y0*n/(a,b) =n;我们也就找到了方程的一个解。



}
} if(a>0) return a; else return(a+n);
mi=m/M[i]; d=ext_euclid(M[i],mi,x,y); a=(a+y*mi*B[i])%m;
练习题目:
中国剩余定理: POJ 1006
数论:素数问题


设m1,m2,…mk是两两互素的正数,则对 任意的整数b1,b2,…bk,同余方程组 x1 ≡ b1 mod m1 x2 ≡ b2 mod m2 … xk ≡ bk mod mk 其解为:



X= (M1’*M1*b1)*(M2’*M2*b2)*…*(Mk’*Mk*bk) mod m; 其中 m = m1*m2*…*mk; Mi = m / mi; Mi’是Mi关于模mi的逆元 Mi X Mi’ = 1(mod mi)
1. 最简单 For(i = 1; i < n;i++) For(i = 1; i < n/2;i++) For(i = 1; i < sqrt(n);i++)
用筛法求素数

厄拉多塞筛法 先将2-N的各数写在纸上: 2,3,4,5,6,7,8,9,10,11,12,13, 14,15,16,17,18,19,20,21,22,23,24, 24,26,27,28,29,30,31,32,33,34,35, 36,37,38,39,40... 在2的上面画一个圆圈,然后划去2的其他倍数; 第一个既未画圈又没有被划去的数是3,将它画圈,再 划去3的其他倍数;现在既未画圈又没有被划去的第一 个数 是5,将它画圈,并划去5的其他倍数……依次类 推,一直到所有小于或等于N的各数都画了圈或划去为 止。这时,表中画了圈的以及未划去的那些数正好就 是小于 N的素数。

}
练习
扩展欧几里德算法: POJ 1061 2115 poj2142:The Balance
中国剩余定理

公元前后的《孙子算经》中有“物不知 数”问题:“今有物不知其数,三三数 之余二 ,五五数之余三 ,七七数之余二, 问物几何?”答为“23”。也就是求同余 式组x≡2 (mod3),x≡3 (mod5 ), x≡2 (mod7)(式中a≡b (mod m) 表示m整除a-b )的正整数解。
y = 0;
return a; }
ret = extended_gcd(b, a % b,x, y); tmp = x; x = y; y = tmp - a / b * y; return ret; }
int main()
{ int a,b,x, y, z; scanf("%d%d",&a,&b); z=extended_gcd(a,b, x, y); printf("%d %d %d\n",z,x,y); return 0; }
代码:形如ax+by=c

int Extended_Euclid(int a,int b,int& x,int &y) { if(b==0){ x=1; y=0; return a; } int d=Extended_Euclid(b,a%b,x,y); int temp=x;x=y;y=temp-a/b*y; return d; } //用扩展欧几里得算法解线性方程ax+by=c; bool linearEquation(int a,int b,int c,int& x,int &y) { int d=Extended_Euclid(a,b,x,y); if(c%d) return false; int k=c/d; x*=k ;// + t*b; y*=k ;//- t*a;//求的只是其中一个解 return true;
练习

??
欧拉函数

在数论,对正整数n,欧拉函数是少于或等于n的数中 与n互质的数的数目。此函数以其首名研究者欧拉命名, 它又称为Euler‘s totient function、φ函数、欧拉商数等。 例如φ(8)=4,因为1,3,5,7均和8互质。 从欧拉函数引伸出来在环论方面的事实和拉格朗 日定理构成了欧拉定理的证明。 φ函数的值 φ(1)=1(唯一和1互质的数就是1本身)。 若n是质数p的k次幂,φ(n)=p^k-p^(k-1)=(p1)p^(k-1),因为除了p的倍数外,其他数都跟n互质。 欧拉函数是积性函数——若m,n互质,



还有一个定理:若gcd(a,b)=1,且x0,y0 为a*x+b*y=n的一组解,则该方程的任一解可 表示为:x=x0+b*t,y=y0-a*t;且对任一整 数t,皆成立。(这个证明比较简单,就不写了) 这样我们就可以求出方程的所有解了,但 实际问题中,我们往往被要求去求最小整数解, 所以我们就可以将一个特解x,t=b/(a,b), x=(x%t+t)%t;就可以了。

若N 通过一次测试,则N 不是素数的概率为 25%,若N 通过t 次测试,则N 不是 素数的概率为1/4**t。事实上取t 为5 时,N 不是素数的概率为 1/128,N 为素数的 概率已经大于99.99%。 在实际应用中,可首先用300—500个小素 数对N 进行测试,以提高拉宾米勒测试 通过的概率,从而提高测试速度。而在生成随 机素数时,选取的随机数最好让 r=0, 则可省去步骤(3) 的测试,进一步提高测试 速度
素性测试:Rabin-Miller算法

数论学家利用费马小定理研究出了多种素数测试方法, 目前最快的算法是拉宾米勒测试算法,(现在不是最 快,印度的一名老师和他的两个本科生的算法是最快 的:印度理工学院计算机科学与工程学系的科学家马 宁德拉· 阿格拉瓦和他的两位在校本科生尼拉叶· 卡雅尔 和尼汀· 萨克斯特纳)其过程如下: (1)计算奇数M,使得N=(2**r)*M+1 (2)选择随机数A<N (3)对于任意i<r,若A**((2**i)*M) MOD N = N-1, 则N通过随机数A的测试 (4)或者,若A**M MOD N = 1,则N通过随机数A的 测试 (5)让A取不同的值对N进行5次测试,若全部通过则 判定N为素数

1.开一个大的bool型数组prime[],大小就是n+1就可以了.先把所有的下标为 奇数的标为true,下标为偶数的标为false. 2.然后: for( i=3; i<=sqrt(n); i+=2 ) { if(prime[i]) for( j=i+i; j<=n; j+=i ) prime[j]=false; } 3.最后输出bool数组中的值为true的单元的下标,就是所求的n以内的素数 了。 原理很简单,就是当i是质(素)数的时候,i的所有的倍数必然是合数。如果i 已经被判断不是质数了,那么再找到i后面的质数来把这个质 数的倍数筛掉。 一个简单的筛素数的过程:n=30。 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
第 1 步过后2 4 ... 28 30这15个单元被标成false,其余为true。 第 2 步开始: i=3; 由于prime[3]=true, 把prime[6], [9], [12], [15], [18], [21], [24], [27], [30]标为false. i=4; 由于prime[4]=false,不在继续筛法步骤。 i=5; 由于prime[5]=true, 把prime[10],[15],[20],[25],[30]标为false. i=6>sqrt(30)算法结束。 第 3 步把prime[]值为true的下标输出来: for(i=2; i<=30; i++) if(prime[i]) printf("%d ",i); 结果是 2 3 5 7 11 13 17 19 23 29
数论
扩展欧几里德算法 中国剩余定理/线性 同余方程 /素数/欧拉函数
扩展欧几里德 算法
欧几里德算法

欧几里德算法又称辗转相除法,用于计 算两个整数a,b的最大公约数。
原理

gcd(a,b) = gcd(b,a mod b) 证明: a可以表示成a = kb + r,则r = a mod b 假设d是a,b的一个公约数,则有d|a, d|b, 而r = a - kb,因此d|r 因此d是(b,a mod b) 的公约数



根据我们前边的结论: a b 都在减小,当 b 减小到 0 时,我们 就可以得出 p = 1 ,q = 0 然后递归回去就可以求出 最终的 p ,q 了
例 注意:形如ax+by = gcd(a,b)
#include<stdio.h>
int extended_gcd(int a, int b, int &x, int &y) { int ret, tmp; if (!b) { x = 1;
它是用来干什么的?



求解模线性方程组(中国余数定理) a ≡ B[1](mod W[1]) a ≡ B[2](mod W[2]) ........ a ≡ B[n](mod W[n])
其中W,B已知,W[i]>0且W[i]与W[j]互质, 求 a
它的原理是什么?






依据以上原理: 经过一步代换必有 a > b 以后的每次代换 将 a 换为 b ,将 b 换为 a % b ,这样 a,b 必定再减小。 当 b 减小到 0 时,它们的最大公因数为 a
实现代码:



int euclid(int a,int b) { if (b==0) return a; else return euclid(b,a%b); }
扩展欧几里德算法
扩展欧几里德算法是用来在已知a, b 求解一组p,q使得p * a+q * b = Gcd(a, b) (解一定存在,根据数论中的相关定理)。

原理


因为Gcd(a, b) = Gcd(b,a%b) 所以p * a+q * b = Gcd(a, b) = Gcd(b,a%b) = p * b + q * a % b = p * b +q * (a – a / b * b) = q * a + (p – a / b*q) *b 这样它就将 a b 的线性组合就化简为 b 与 a % b 的线性组合。
1. φ(mn)=φ(m)φ(n) 2. φ(p)=p-1 p为素数 φ (p^n)=p^(n-1)*(p-1); 3. a是N的质因数 若(N%a==0 && (N/a)%a==0) 有:E(N)=E(N/a)*a; 若(N%a==0 && (N/a)%a!=0) 有:E(N)=E(N/a)*(a-1); 欧拉函数的引伸:小于或等于n的数中,与n互质的数 的总和为:φ(x) * x / 2。(n>1)
相关文档
最新文档