使用C# 判断给定大数是否为质数的详解

2016-02-19 09:11 10 1 收藏

下面图老师小编要向大家介绍下使用C# 判断给定大数是否为质数的详解,看起来复杂实则是简单的,掌握好技巧就OK,喜欢就赶紧收藏起来吧!

【 tulaoshi.com - 编程语言 】

C#判断给定大数是否为质数,目标以快速度得到正确的计算结果。
在看到这道题的时候,第一反应这是一道考程序复杂度的题,其次再是算法问题。
我们先来看看质数的规则:
Link:http://en.wikipedia.org/wiki/Prime_number
C#求质数代码:
代码如下:

public bool primeNumber(int n){
             int sqr = Convert.ToInt32(Math.Sqrt(n));
             for (int i = sqr; i 2; i--){
                 if (n % i == 0){
                     b = false;
                 }
             }
             return b;
         }

显然以上代码的程序复杂度为N
我们来优化下代码,再来看下面代码:
代码如下:

public bool primeNumber(int n)
         {
             bool b = true;
             if (n == 1 || n == 2)
                 b = true;
             else
             {
                 int sqr = Convert.ToInt32(Math.Sqrt(n));
                 for (int i = sqr; i 2; i--)
                 {
                     if (n % i == 0)
                     {
                         b = false;
                     }
                 }
             }
             return b;
         }

通过增加初步判断使程序复杂度降为N/2。
以上两段代码判断大数是否质数的正确率是100%,但是对于题干
  1.满足大数判断;
  2.要求以最快速度得到正确结果;
显然是不满足的。上网查了下最快算法得到准确结果,公认的一个解决方案是Miller-Rabin算法
Link:http://en.wikipedia.org/wiki/Miller%E2%80%93Rabin_primality_test
Miller-Rabin 基本原理是通过随机数算法判断的方式提高速度(即概率击中),但是牺牲的是准确率。
Miller-Rabin 对输入大数的质数判断的结果并不一定是完全准确的,但是对于本题来说算是一个基本的解题办法了。
Miller-Rabin C# 代码:
代码如下:

public bool IsProbablePrime(BigInteger source) {
             int certainty = 2;
             if (source == 2 || source == 3)
                 return true;
             if (source 2 || source % 2 == 0)
                 return false;

             BigInteger d = source - 1;
             int s = 0;

             while (d % 2 == 0) {
                 d /= 2;
                 s += 1;
             }

             RandomNumberGenerator rng = RandomNumberGenerator.Create();
             byte[] bytes = new byte[source.ToByteArray().LongLength];
             BigInteger a;

             for (int i = 0; i certainty; i++) {
                 do {
                     rng.GetBytes(bytes);
                     a = new BigInteger(bytes);
                 }
                 while (a 2 || a = source - 2);

                 BigInteger x = BigInteger.ModPow(a, d, source);
                 if (x == 1 || x == source - 1)
                     continue;

                 for (int r = 1; r s; r++) {
                     x = BigInteger.ModPow(x, 2, source);
                     if (x == 1)
                         return false;
                     if (x == source - 1)
                         break;
                 }

                 if (x != source - 1)
                     return false;
             }

             return true;
         }

来源:http://www.tulaoshi.com/n/20160219/1589857.html

延伸阅读
如同java一样,在c#中写一个多线程应用是非常简单的,本章将介绍如何在c#种开发多线程程序。在.net中线程是由System.Threading 名字空间所定义的。所以你必须包含这个名字空间。 using System.Threading; 开始一个线程 System.Threading 名字空间的线程类描述了一个线程对象,通过使用类对象,你可以创建、删除、停止及恢复一个线程。创建一个...
第四章:C# 中的加框与去框 C# 运行时中有两种类型:引用类型(reference)(在 C# 中用类声明)和值类型(value)(在 C# 中用结构声明)。引用和值类型在几个重要方面有所不同。值类型感觉上象一个数据。它包括预定义数值类型(如int、bool)以及用户定义的类型(circle、Point等)。如上文所述,值类型的变量是实际的值,所以在您使用变量时,通...
摘要:本文论述了各种模式的线程(单线程、单元线程和自由线程)以及每种模式的使用方法。同时,还提供了一个使用线程的 C# 语言代码示例,以帮助您编写使用线程的应用程序。本文还讨论了多线程代码中的一些重要问题。 简介 编写多线程 Microsoft® 消息队列 (MSMQ) 触发器应用程序向来是一件让人畏惧的事情。不过,.NET 框架...
    我感觉声音的播放比较简单。我们从播放声音开始。为什么我这么觉得?我也不知道。 这里是展示最最最最最简单的DirectX播放声音的例子,我尽量省略了无关的代码。最后的代码只有19行,够简单了吧? 准备工作: 1.安装了DirectX SDK(有9个DLL文件)。这里我们只用到MicroSoft.DirectX.dll 和 Microsoft.Directx.DirectSound...
类(class)是C#类型中最基础的类型。类是一个数据结构,将状态(字段)和行为(方法和其他函数成员)组合在一个单元中。类提供了用于动态创建类实例的定义,也就是对象(object)。类支持继承(inheritance)和多态(polymorphism),即派生类能够扩展和特殊化基类的机制。使用类声明可以创建新的类。类声明以一个声明头开始,其组成方式如...

经验教程

648

收藏

100
微博分享 QQ分享 QQ空间 手机页面 收藏网站 回到头部