在前面的章节中,我们分别讨论了质数和指数,今天我们不做其他的,仅仅将它们进行整合一下,为什么呢?因为在数学领域,有一种特殊的正整数,形如:2^p - 1,其中指数p为质数,这种数字被称为梅森数,其中的质数又被称为梅森素数。

梅森数中有一种“变体”——伪素数:2^(p-1)-1,它能被p整除,同时p又为非偶数的合数。

OK,今天我们用JAVA语言来针对这几个特殊数字进行编译。

一、梅森数

我们先根据梅森数的公式自定一个方法用以计算梅森数:

/**

* 计算梅森数

*

* @param number

* @return

*/

private static BigDecimal calculateMersenneNumber(BigDecimal number) {

// TODO Auto-generated method stub

return integerMi(BigDecimal.valueOf(2), number).subtract(BigDecimal.ONE);

}

上述这个方法仅仅是用以计算2^p - 1的结果,因此我们在main()方法体中编译代码时需要“提取”质指数:

for (BigDecimal a = BigDecimal.valueOf(2); a.compareTo(BigDecimal.valueOf(100)) <= 0; a = a.add(BigDecimal.ONE))

if (primeNumber(a))

System.out.println("2 ^ " + a + " - 1 = " + calculateMersenneNumber(a));

运行结果:

2 ^ 2 - 1 = 3

2 ^ 3 - 1 = 7

2 ^ 5 - 1 = 31

2 ^ 7 - 1 = 127

2 ^ 11 - 1 = 2047

2 ^ 13 - 1 = 8191

2 ^ 17 - 1 = 131071

2 ^ 19 - 1 = 524287

2 ^ 23 - 1 = 8388607

2 ^ 29 - 1 = 536870911

2 ^ 31 - 1 = 2147483647

2 ^ 37 - 1 = 137438953471

2 ^ 41 - 1 = 2199023255551

2 ^ 43 - 1 = 8796093022207

2 ^ 47 - 1 = 140737488355327

2 ^ 53 - 1 = 9007199254740991

2 ^ 59 - 1 = 576460752303423487

2 ^ 61 - 1 = 2305843009213693951

2 ^ 67 - 1 = 147573952589676412927

2 ^ 71 - 1 = 2361183241434822606847

2 ^ 73 - 1 = 9444732965739290427391

2 ^ 79 - 1 = 604462909807314587353087

2 ^ 83 - 1 = 9671406556917033397649407

2 ^ 89 - 1 = 618970019642690137449562111

2 ^ 97 - 1 = 158456325028528675187087900671

根据梅森数的定义我们计算出了指数p在前100以内的所有梅森数。

二、梅森素数

梅森素数也是梅森数,只不过它将“梅森合数”舍弃了,因此我们在输出梅森素数时只需在main()方法体中梅森数的源代码中加入一个条件语句,用以限制输出时只输出梅森素数即可。

for (BigDecimal a = BigDecimal.valueOf(2); a.compareTo(BigDecimal.valueOf(100)) <= 0; a = a.add(BigDecimal.ONE))

if (primeNumber(a) && primeNumber(calculateMersenneNumber(a)))

System.out.println("2 ^ " + a + " - 1 = " + calculateMersenneNumber(a));

运行结果:

2 ^ 2 - 1 = 3

2 ^ 3 - 1 = 7

2 ^ 5 - 1 = 31

2 ^ 7 - 1 = 127

2 ^ 13 - 1 = 8191

2 ^ 17 - 1 = 131071

2 ^ 19 - 1 = 524287

…………………………

它得先计算,在判断是否为素数,运行时间相当长,因此我只选取了指数在20以内的。

三、伪素数

同样,我们先根据伪素数的公式自定一个方法用以计算伪素数:

/**

* 计算伪素数

*

* @param number

* @return

*/

private static BigDecimal calculatePseudoPrimeNumber(BigDecimal number) {

// TODO Auto-generated method stub

return integerMi(BigDecimal.valueOf(2), number.subtract(BigDecimal.ONE)).subtract(BigDecimal.ONE);

}

就如同上述计算梅森数和梅森素数一样,在编译main()方法体中的代码时,我们也需要根据伪素数的定义对2的指数进行一定的限制;并且我们多加一个步骤,就是对其进行质数分解。

为此我们编译出了如下代码:

for (BigDecimal a = BigDecimal.valueOf(2);; a = a.add(BigDecimal.ONE))

if (calculatePseudoPrimeNumber(a).remainder(a).equals(BigDecimal.ZERO) && !primeNumber(a)

&& a.remainder(BigDecimal.valueOf(2)).equals(BigDecimal.ONE)) {

System.out.print("2 ^ ( " + a + " - 1 ) - 1 | " + a + " = ");

divisorPrime(a);

System.out.println();

}

PS:我们看伪素数的公式:2^(p-1)-1能被p整除,最小的伪素数为341,那么带入公式,其输出的结果也是非常大的,因此我们在此省却此类结果的输出,仅仅用公式表达伪素数的含义,并且对伪素数进行质数分解。

运行结果:

2 ^ ( 341 - 1 ) - 1 | 341 = 11 * 31

2 ^ ( 561 - 1 ) - 1 | 561 = 3 * 11 * 17

2 ^ ( 645 - 1 ) - 1 | 645 = 3 * 5 * 43

2 ^ ( 1105 - 1 ) - 1 | 1105 = 5 * 13 * 17

2 ^ ( 1387 - 1 ) - 1 | 1387 = 19 * 73

2 ^ ( 1729 - 1 ) - 1 | 1729 = 7 * 13 * 19

2 ^ ( 1905 - 1 ) - 1 | 1905 = 3 * 5 * 127

2 ^ ( 2047 - 1 ) - 1 | 2047 = 23 * 89

2 ^ ( 2465 - 1 ) - 1 | 2465 = 5 * 17 * 29

2 ^ ( 2701 - 1 ) - 1 | 2701 = 37 * 73

2 ^ ( 2821 - 1 ) - 1 | 2821 = 7 * 13 * 31

………………………………

PS:“|”代表前者可以被后者整除。

java梅森素数_JAVA基础 第三篇:梅森数、梅森素数、伪素数——素数与指数的完美结合与进阶...相关推荐

  1. JavaScrip 基础 第三篇

    JavaScrip 基础 第三篇 JS分支结构 流程控制 在一个程序执行的过程中 ,各条代码执行顺序对程序结果是有直接影响的,很多时候需要通过控制代码 执行顺序来实现完成的功能 简单理解:流程控制就是 ...

  2. Java并发编程之CAS第三篇-CAS的缺点

    Java并发编程之CAS第三篇-CAS的缺点 通过前两篇的文章介绍,我们知道了CAS是什么以及查看源码了解CAS原理.那么在多线程并发环境中,的缺点是什么呢?这篇文章我们就来讨论讨论 本篇是<凯 ...

  3. java单线程循环调度_Java基础篇之Java线程模型

    原标题:Java基础篇之Java线程模型 Java运行系统在很多方面依赖于线程,所有的类库设计都考虑到多线程.实际上,Java使用线程来使整个环境异步.这有利于通过防止CPU循环的浪费来减少无效部分. ...

  4. java定义构造方法_JAVA基础学习之路(三)类定义及构造方法

    类的定义及使用 一,类的定义 classBook {//定义一个类intprice;//定义一个属性intnum;public static int getMonney(int price, intn ...

  5. java 打印三维数组_Java基础第三天_数组

    1.定义一个函数,函数功能是动态提取int[]中元素的最大值. 2.定义一个函数,从数组中查询指定的元素首次出现的位置. 3.定义函数,完成冒泡排序,大数下沉. 4.折半查找. 5.阐述 6.定义一个 ...

  6. java基本类型有缓冲区类型的有_Java基础(三十四)String、StringBuffer类和数据缓冲区Buffer类...

    一.String类 1.创建字符串对象 创建字符串对象有两种方法:直接用"="或者使用"new String(...)" String aStr = " ...

  7. java getinstance 反射_Java 基础篇之反射

    使用反射获取程序运行时的对象和类的真实信息. 获取 Class 对象 每个类被加载之后,系统会为该类生成一个对应的 Class 对象,通过该 Class 对象可以访问到 JVM 中的这个类. 使用 C ...

  8. 三 java的基本数据类型_JAVA基础(三)--JAVA基本数据类型

    前两篇已经将开发环境搭建完成,如果你已经按之前的教程按部就班的完成了部署,那么世界上最优秀的编程语言之一和世界上最优秀的IDE之一已经出现在你的电脑上(此处应有掌声),如果你还没入门,或者正在台阶上踱 ...

  9. java 随机句子_Java基础三(Scanner键盘输入、Random随机数、流程控制语句)

    1.引用类型变量的创建及使用 2.流程控制语句之选择语句 3.流程控制语句之循环语句 4.循环高级 ###01创建引用类型变量公式 * A: 创建引用类型变量公式 * a: 我们要学的Scanner类 ...

最新文章

  1. 几步教你轻松搭建一个Java Web项目
  2. SLAM和三维重建有什么区别?
  3. wp-login.php 404页面,wordpress隐藏后台登陆界面,自动跳转首页或404
  4. 政府门户网站建设解决方案
  5. 综合布线工作组2009年工作简报
  6. (转)The Standard C Library 经典的基础(下)
  7. 【转】Nginx服务并发过10万的Linux内核优化配置
  8. disruptor小结--消费者
  9. 阶段1 语言基础+高级_1-3-Java语言高级_05-异常与多线程_第3节 线程同步机制_5_同步技术的原理...
  10. matlab中最好用的滤波函数,matlab中滤波函数
  11. python超简单语音识别
  12. 搭建网站服务器必须开443端口,记录解决网站443端口不通的问题(启动HTTP或者更换域名)...
  13. 红黑树的插入与验证——附图详解
  14. VC++操作Excel生成饼状图!
  15. uni-app中兴趣标签选择
  16. 开放式视觉伺服平台源代码_上位机(初步版本,未对细节做修订)
  17. Lombok最全使用详解
  18. 总结一波 Redis 面试题
  19. 推荐10大协作工具,测试团队必备
  20. English语法_ 5大句型

热门文章

  1. 最短编辑距离问题理解
  2. 几款让你爱不释手的语音转文字软件
  3. Android 动画 介绍与使用
  4. java常用API之DateFormat
  5. SAP CRM 使用Javascript触发SAP Server Event
  6. 在linux的weblogic上增加启动参数
  7. Centos 7 更改网卡名字
  8. Linux下arp用法
  9. 求助关于系统日志的解决方案
  10. 百题大冲关系列课程更新啦!这次是 Golang