附 原
始
实
验
记
录
| 1.欧几里得算法实验:设 a 为自己的学号,b=210,编程实现扩展的欧几里得算法,并求整数s[n]、t[n],使得 s[n]a+t[n]b=(a, b)。 (1)根据以下代码,编程实现扩展的欧几里得算法,输出计算的中间结果及最终运算结果。 def ext_gcd(a, b): if b == 0: x1 = 1 y1 = 0 x = x1 y = y1 r = a return r, x, y else: r, x1, y1 = ext_gcd(b, a % b) x = y1 y = x1 - a // b * y1 return r, x, y print(str(a) + '=' +str(a//b)+'×'+str(b)+'+' + str(a%b)) print(str(r) + '=' + str((a)) + '×' + str(x) + '+' + str(b)+ '×'+str(y)) print('裴蜀等式:'+str(r)+'='+str(a)+'×'+str(x)+'+'+str(b)+'×'+str(y)) (2)代码如下: def ext_gcd(a, b): if b == 0: x1 = 1 y1 = 0 x = x1 y = y1 r = a return r, x, y else: print(str(a) + '=' +str(a//b)+'×'+str(b)+'+' + str(a%b)) r, x1, y1 = ext_gcd(b, a % b) x = y1 y = x1 - a // b * y1 if x!=0: print(str(r) + '=' + str((a)) + '×' + str(x) + '+' + str(b)+ '×'+str(y)) return r, x, y if __name__ == '__main__': a=20101030210; b=210; r, x, y=ext_gcd(a, b) print('裴蜀等式:'+str(r)+'='+str(a)+'×'+str(x)+'+'+str(b)+'×'+str(y))

2.素性检测算法实验:设a为自己的学号后两位+100,编程实现Miller-Rabin素性检测算法,找出使得离a最近且比a大的三个素数。 (1)Miller-Rabin素性检测算法python语言代码 import math import random
# 使用平方乘算法,计算a**b(mod n)。 def SquareMultiplication(a, b, n): # 将b表示为二进制形式bkbl-1...b0,既b=bn*2**n+bn-1*2**(n-1)+...+b1*2**1+b0*2**0 b_bin = bin(b)[2:][::-1] r=1 #a**b=(((((1**2*a**bn)**2*a**bn-1)**2...a**b2)**2)*a**b1)**2*a**b0 for i in list(range(len(b_bin)))[::-1]: r=r*r*a**int(b_bin[i])%n return r # 使用模重复平方算法,计算a**b(mod n)。 def ModRepeatSquare(a, b, n): # 将b表示为二进制形式bkbk-1...b0,既b=bk*2**k+bk-1*2**(k-1)+...+b1*2**1+b0*2**0 b_bin = bin(b)[2:][::-1] r=1 #a**b=a**b0*(a**2)**b1...(a**2**k-1)**bk-1*(a**2**k)**bk for i in list(range(len(b_bin))): if b_bin[i]=='1':r=a*r%n a=a*a%n return r
#欧几里得算法,求最大公约数 def gcd(a, b): if b == 0: return a else: r = gcd(b, a % b) return r
# 如果返回值为TRUE表示n为素数,返回值为FALSE表示n为合数。 def MillerRabinPrimeTest(n): a = random.randint(2, n - 2) # 随机第选取一个a∈[2,n-2] if gcd(a, n)>1: return False s = 0 # s为d中的因子2的幂次数。 t = n - 1 while (t & 1) == 0: # 将d中因子2全部提取出来。 s += 1 t >>= 1
x = ModRepeatSquare(a, t, n) for i in range(s): # 进行s次二次探测 newX = ModRepeatSquare(x, 2, n) if newX == 1 and x != 1 and x != n - 1: return False # 用二次探测定理的逆否命题,此时n确定为合数。 x = newX
if x != 1: # 用费马小定理的逆否命题判断,此时x=a^(n-1) (mod n),那么n确定为合数。 return False
return True # 用费马小定理的逆命题判断。能经受住考验至此的数,大概率为素数。
# 经过连续特定次数(如100次)的Miller-Rabin测试后, # 如果返回值为TRUE表示n为素数,返回值为FALSE表示n为合数。 def isPrimeByMRS(n): if n<=3 or (n & 1) == 0: return False for i in range(100): if MillerRabinPrimeTest(n) == False: return False return True
if __name__ == '__main__': random.seed() #a为自己的学号后两位+100,如学号后两位为07 a = 110 for i in range(a, a + 10): result = isPrimeByMRS(i) if result == True: print("离a最近且比a大的三个素数为:%d" %(i))

3. 模重复平方算法实验: 实现的python代码如下: def SquareMultiplication(a, b, n): # 将b表示为二进制形式bkbl-1...b0,既b=bn*2**n+bn-1*2**(n-1)+...+b1*2**1+b0*2**0 b_bin = bin(b)[2:][::-1] r=1 #a**b=(((((1**2*a**bn)**2*a**bn-1)**2...a**b2)**2)*a**b1)**2*a**b0 for i in list(range(len(b_bin)))[::-1]: r=r*r*a**int(b_bin[i])%n return r # 使用模重复平方算法,计算a**b(mod n)。 def ModRepeatSquare_10(a_10, b_10, n_10): # 将b表示为二进制形式bkbk-1...b0,既b=bk*2**k+bk-1*2**(k-1)+...+b1*2**1+b0*2**0 b_10_bin = bin(b_10)[2:][::-1] r_10=1 #a**b=a**b0*(a**2)**b1...(a**2**k-1)**bk-1*(a**2**k)**bk for i in list(range(len(b_10_bin))): if b_10_bin[i]=='1':r_10=a_10*r_10%n_10 a_10=a_10*a_10%n_10 print('第'+ str(i)+ '轮, m['+str(i) + ']=' + str(b_10 & 1) + ',r['+str(i)+']='+ str(r_10) + '(mod'+str(n_10)+ '),a['+str(i)+ ']='+str(a_10)) else: print('第'+ str(i) + '轮,m['+ str(i)+ ']='+ str(b_10 & 1) + ',r['+ str(i)+']='+'r['+str( i- 1) + ']×'+ 'a['+ str(i - 1)+ ']='+ str(r_10) + '(mod'+ str(n_10) + '),a['+str(i)+']='+str(a_10)) return r_10
if __name__ == '__main__': print("使用模重复平方法计算a**m(mod n),请输入数字a:"); a_10 = int(input()); print("请输入数字m:"); b_10 = int(input()); print("请输入数字n:"); n_10 = int(input()); result_10 = ModRepeatSquare_10(a_10, b_10, n_10) print('结果为:'+str(a_10)+'**'+str(b_10)+'(mod '+str(n_10)+')'+'='+str(result_10))



4.算法实验: 开RSA源码文件夹,熟悉RSA算法流程,将公钥(e,n)中的e改为学号后5位,e=30210

五、实验思考 - 源程序中采用的哪种快速运算算法?拓展欧几里得算法、Miller-Rabin素性检测算法、模重复平方算法
- 如何确保大素数p和q是满足条件的大素数呢?费马素性检测,通过费马小定理:如果p是一个素食,且整数a不是p的倍数,那么a^p-1=1(modp)
- 正整数e一般建议选取多少?为什么?
一般建议取e=2^16+1=65537. 六、实验算例 设p=43,q=59,取公钥e=13+学号后两位=23,用RSA算法加密明文public。将明文代替为数字,代替方案为a-00,b-01,...,z-25(两位十进制数表示),既public=162102120903;并利用RSA算法实验

|