大家都知道RSA的加密的安全性就是能够找到一个合适的大素数,而现在判断大素数的办法有许多,比如Fermat素性测试或者Miller-Rabin素性测试,而这里我用了Miller-Rabin素性测试的算法,具体的理论我写到下面。

算法的理论基础:

  1. Fermat定理:若n是奇素数,a是任意正整数(1≤ a≤ n−1),则 a^(n-1) ≡ 1 mod n。

2.  如果n是一个奇素数,将n−1表示成2^s*r的形式,r是奇数,a与n是互素的任何随机整数,那么a^r ≡ 1 mod n或者对某个j (0 ≤ j≤ s−1, j∈Z) 等式a^(2jr) ≡ −1 mod n 成立。

实验需要根据这个算法的理论来实现对素数的判定功能,而我将上述理论用C++的 形式写了出来,然后在一些细节的算法上少做润色,成功实现了对素数的生成和判定。

一、实验代码:

#include<iostream>

#include<cmath>

#include<ctime>

#include<cstdlib>

using namespace std;

typedef unsigned long long ll;

long long q_mul( long long a, long long b, long long mod )

{

long long ans = 0;

while(b)

{

if(b & 1)

{

b--;

ans =(ans+ a)%mod;

}

b /= 2;

a = (a + a) % mod;

}

return ans;

}

long long q_pow( long long a, long long b, long long mod )

{

long long ans = 1;

while(b)

{

if(b & 1)

{

ans = q_mul( ans, a, mod );

}

b /= 2;

a = q_mul( a, a, mod );

}

return ans;

}

//long long q_pow(ll a,ll b,ll mod){

// ll base=a;

// ll ans = 1;

// while(b!=0){

// if(b&1) ans = (ans*base)%mod;

// base = (base*base)%mod;

// b>>=1;

// }

// return ans;

//}

int Miller_Rabin(ll n) {

if(n<2) return 0;

if(n==2) return 1;

ll k=0,q=n-1;

while(q%2==0){

q=q/2;

k++;

}

ll a = rand(); //要保证a在(1,n-1)之间,开区间

a=(a%(n-2))+2;

ll result1 = q_pow(a,q,n);

if(result1 == 1||result1 == n-1){

return 1;

}

while(k--){

result1 = q_mul(result1,2,n);

if(result1 == n-1) return 1;

}

return 0;

}

bool True_Miller_Rabin(ll n){

int times = 10;

while(times){

times--;

if(Miller_Rabin(n)==0) return false;

}

return true;

}

int main()

{

srand((unsigned)time(NULL));

ll num;

// while(1){

// cin>>num;

// if(Miller_Rabin(num)==1)

// cout<<"为素数"<<endl;

// else{

// cout<<"是合数"<<endl;

// }

// }

for(ll i=1000000;i<=1005000;i++){

int a =0;

if(True_Miller_Rabin(i)){

cout<< i<<"是素数"<<endl;

}

}

return 0;

}

二、实验结果(自行测试)

这是对1000000000000000000到1000000000000005000里所有素数判定的结果

这是对输入素数的判读

以上结果说明,该程序完全能够胜任在long long类型范围下的素数判定任务。

三、实验总结

本次实验采用了Miller-Rabin算法,而在理解算法的基础上我们要灵活运用。在算法中我最开始用到了C++函数里面的pow函数,然而这个函数导致我素数输出不完整,经过很久的调试,我发现是C++自带库里面的数据类型与long long类型有出入,所以我放弃了使用自带的函数库。之后,我选择了快速幂算法。这个算法比pow函数效果更好,能够对大数进行快速的幂计算。然而在快速幂计算的过程中设计到两个数相乘,当两个Long 类型的数据相乘时会溢出从而导致计算的大素数长度有限。于是我有考虑将幂计算里面的乘法分成若干个加法去进行运算,于是我采用了快速乘与快速幂想结合的方式,也就是我上述代码中绿色的部分(蓝色部分为单纯快速幂),由此我讲幂运算的速度有提升了一个档次,在此基础上也增大了计算素数的范围。

——————Made By Pinging、、、、、hhh  Welcome to CUMT。。。

记一次使用快速幂与Miller-Rabin的大素数生成算法的更多相关文章

  1. TZOJ 5291 游戏之合成(快速幂快速乘)

    描述 zzx和city在玩一款小游戏的时候,游戏中有一个宝石合成的功能,需要m个宝石才可以合成下一级的宝石(例如需要m个1级宝石才能合成2级宝石). 这时候zzx问city说“我要合成A级宝石需要多少 ...

  2. 二分求幂/快速幂取模运算——root(N,k)

    二分求幂 int getMi(int a,int b) { ; ) { //当二进制位k位为1时,需要累乘a的2^k次方,然后用ans保存 == ) { ans *= a; } a *= a; b / ...

  3. 递归实现快速幂(C++版)

    快速幂是什么? 顾名思义,快速幂就是快速算底数的n次幂.其时间复杂度为 O(log₂N), 与朴素的O(N)相比效率有了极大的提高. 就以a的b次方来介绍: 把b转换成二进制数,该二进制数第i位的权为 ...

  4. 洛谷P3758/BZOJ4887 [TJOI2017] 可乐 [矩阵快速幂]

    洛谷传送门,BZOJ传送门 可乐 Time Limit: 10 Sec  Memory Limit: 64 MBSubmit: 299  Solved: 207 Description 加里敦星球的人 ...

  5. $Miller Rabin$总结

    \(Miller Rabin\)总结: 这是一个很高效的判断质数的方法,可以在用\(O(logn)\) 的复杂度快速判断一个数是否是质数.它运用了费马小定理和二次探测定理这两个筛质数效率极高的方法. ...

  6. 关于素数:求不超过n的素数,素数的判定(Miller Rabin 测试)

    关于素数的基本介绍请参考百度百科here和维基百科here的介绍 首先介绍几条关于素数的基本定理: 定理1:如果n不是素数,则n至少有一个( 1, sqrt(n) ]范围内的的因子 定理2:如果n不是 ...

  7. 【66测试20161115】【树】【DP_LIS】【SPFA】【同余最短路】【递推】【矩阵快速幂】

    还有3天,今天考试又崩了.状态还没有调整过来... 第一题:小L的二叉树 勤奋又善于思考的小L接触了信息学竞赛,开始的学习十分顺利.但是,小L对数据结构的掌握实在十分渣渣.所以,小L当时卡在了二叉树. ...

  8. hdu 1568 Fibonacci 快速幂

    Fibonacci Time Limit: 1000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Proble ...

  9. BZOJ_[HNOI2008]_Cards_(置换+Burnside引理+乘法逆元+费马小定理+快速幂)

    描述 http://www.lydsy.com/JudgeOnline/problem.php?id=1004 共n个卡片,染成r,b,g三种颜色,每种颜色的个数有规定.给出一些置换,可以由置换得到的 ...

随机推荐

  1. MySQL(二)之服务管理与初始化文件修改和连接MySQL

    上一篇给大家介绍了怎么在linux和windows中安装mysql,本来是可以放在首页的,但是博客园说“安装配置类文件”不让放在首页.接下来给大家介绍一下在linux和windows下MySQL的一下 ...

  2. Cython的用法以及填坑姿势

    因为项目需要,需要优化已有的Python代码.目前Python代码的执行过程是将Python代码转变成一行行指令,然后解释器解释指令的执行,调用到C代码层.如果去掉指令解释这个阶段,直接进入C代码层, ...

  3. [js高手之路]深入浅出webpack教程系列3-配置文件webpack.config.js详解(下)

    本文继续接着上文,继续写下webpack.config.js的其他配置用法. 一.把两个文件打包成一个,entry怎么配置? 在上文中的webpack.dev.config.js中,用数组配置entr ...

  4. springboot 入门二- 读取配置信息一

    在上篇入门中简单介绍下springboot启动使用了大量的默认配置,在实际开发过程中,经常需要启动多个服务,那端口如何手动修改呢? 此篇就是简单介绍相关的配置文件信息. Spring Boot允许外部 ...

  5. Java 优先队列

    Java PriorityQueue 优先队列是一种重要的数据结构,其利用的是小/大顶堆来实现的. Java中提供了PriorityQueue,PriorityQueue是基于小顶堆实现的无界优先队列 ...

  6. C++IO类&文件输入输出

    C++IO类&文件输入输出 istream(输入流)类型,提供输入操作. ostream(输出流)类型,提供输出操作. cin,一个istream对象,从标准输入读取数据. cout,一个os ...

  7. OpenSSL中的大数接口与基于其的自用RSA加密接口设计

    本文记录了初次接触OpenSSL中的大数模块,重温了RSA加密流程,使用OpenSSL的接口包装成自用RSA加密接口,并且利用自己的接口演示了Alice与Bob通过RSA加密进行通讯的一个示例. 概览 ...

  8. 个人作业3——个人总结(Alpha阶段)

    个人总结 Alpha阶段总结: 起初关于手机app的开发真的一无所知,选了一条较远的路走(使用 Android Studio 来开发 Android 应用更加方便,而我们选用 Eclipse 开发 A ...

  9. 【2017集美大学1412软工实践_助教博客】团队作业5——测试与发布(Alpha版本)

    第五次团队作业成绩公布 题目 团队作业5: http://www.cnblogs.com/happyzm/p/6788792.html 团队成绩 成绩公示如下: 检查项 测试报告 Alpha版本发布说 ...

  10. 结队编程-基于gui的四则运算生成器

    成员:卢少锐 201421123027.刘存201421033023 coding.net地址 1.需求分析:除了实现四则运算的功能外,还添加了计时器功能和语言选择功能 2.程序设计:这次作业是基于上 ...