乡下人产国偷v产偷v自拍,国产午夜片在线观看,婷婷成人亚洲综合国产麻豆,久久综合给合久久狠狠狠9

  • <output id="e9wm2"></output>
    <s id="e9wm2"><nobr id="e9wm2"><ins id="e9wm2"></ins></nobr></s>

    • 分享

      淺談隨機(jī)數(shù)發(fā)生器 原創(chuàng) 2013年12月19日 01:51:28 標(biāo)簽:隨機(jī) /隨機(jī)數(shù)

       小橋流水ytff06 2018-01-29

           今天在微博上到一篇如何使用隨機(jī)數(shù)的文章,讓我回憶起剛上大一時學(xué)C語言時,書后有道調(diào)用rand()函數(shù)的練習(xí)題,當(dāng)時覺得好神奇,想知道它是怎么實(shí)現(xiàn)的,大二時候?qū)WJava又遇到了random()函數(shù),恰巧當(dāng)時上機(jī)課我有機(jī)會問老師,遺憾的是老師只是告訴我那是偽隨機(jī)數(shù),課后查查資料才了解。如今來一篇關(guān)于隨機(jī)數(shù)發(fā)生器博文來回憶一下神奇的隨機(jī)數(shù)。

           眾所周知,我們平時所使用的無論什么編程語言都會提供一個隨機(jī)數(shù)函數(shù),而且它是偽隨機(jī)數(shù)(Pseudo Random Number),它是由算法計(jì)算得出的,是可以預(yù)測的,也就是說當(dāng)隨機(jī)種子相同時,對于同一個隨機(jī)函數(shù),得出的隨機(jī)數(shù)列是固定不變的,亞裔唯一圖靈獎得主姚期智就是研究的就是偽隨機(jī)數(shù)生成論;與之對應(yīng)的就是真隨機(jī)數(shù)(True Random Number)它是真正的隨機(jī)數(shù),無法預(yù)測且無周期性;還有一種是產(chǎn)生隨機(jī)數(shù)的發(fā)生器是密碼學(xué)偽隨機(jī)數(shù)發(fā)生器(Cryptographically Secure Pseudo-Random Number Generator)常用的算法有 MD5 ,SHA1 等標(biāo)準(zhǔn), 這里不做過多討論,說說最基本的前兩種:


      一、真隨機(jī)數(shù)發(fā)生器

          像無法實(shí)現(xiàn)永動機(jī)一樣,想要實(shí)現(xiàn)真隨機(jī)數(shù)靠程序是永遠(yuǎn)無法實(shí)現(xiàn)的,很多情況下只能看老天的眼色,比如布朗運(yùn)動,量子效應(yīng),放射性衰變等。第一個真隨機(jī)數(shù)發(fā)生器是1955年由Rand公司創(chuàng)造的,而在1999年,intel發(fā)布Intel810芯片組時,就配備了硬件隨機(jī)數(shù)發(fā)生器,基于IntelRNG的真隨機(jī)數(shù)生成器可以生成滿足獨(dú)立性和分布均勻性的真隨機(jī)數(shù),目前大部分芯片廠商都集成了硬件隨機(jī)數(shù)發(fā)生器,只要安裝相應(yīng)驅(qū)動,了解讀取寄存器地址,可以直接調(diào)用發(fā)生器。Intel810RNG的原理大概是:利用熱噪聲(是由導(dǎo)體中電子的熱震動引起的)放大后,影響一個由電壓控制的振蕩器,通過另一個高頻振蕩器來收集數(shù)據(jù)。TRNG的類型主要有:

      1.基于電路的TRNG:

      i.振蕩器采樣:就是上述Intel采用的方式。

      ii.直接放大電路噪聲:利用電路中各種噪聲,如上述的熱噪聲作為隨機(jī)源,由于強(qiáng)度小,所以先要對其放大,然后對一定時間內(nèi)超過閾值的數(shù)據(jù)進(jìn)行統(tǒng)計(jì),這樣就產(chǎn)生的隨機(jī)數(shù)。.

      iii.電路亞穩(wěn)態(tài):亞穩(wěn)態(tài)表示觸發(fā)器無法在規(guī)定時間內(nèi)達(dá)到一個可確認(rèn)狀態(tài),一定條件下,觸發(fā)器達(dá)到兩個穩(wěn)態(tài)的幾率為50%,所以先使電路進(jìn)入亞穩(wěn)態(tài),之后根據(jù)狀態(tài)轉(zhuǎn)化為隨機(jī)數(shù)。

      iv.混沌電路:不可預(yù)測,對初始條件的敏感的依賴性。以及混沌電路在芯片中易于實(shí)現(xiàn)的特點(diǎn),可以產(chǎn)生效果不錯的隨機(jī)數(shù)。

      2.基于其他物理源的TRNG

      如宇宙射線,粒子衰變,空氣噪聲等作為隨機(jī)源,來產(chǎn)生隨機(jī)數(shù)。

      3.其他物理信息TRNG

      人為可以產(chǎn)生隨機(jī)數(shù)嗎?當(dāng)然能!聽說一個HR拆選簡歷的方式是往天上一扔,掉在桌子上的簡歷就通過,這個HR確認(rèn)懂隨機(jī)啊,而且是真隨機(jī)。這類隨機(jī)生活中隨處可見,擲骰子,抓麻將,或者統(tǒng)計(jì)一個月內(nèi)帝都PM2.5的數(shù)值。

      對于真隨機(jī)發(fā)生器我個人認(rèn)為未來是可以通過生物計(jì)算機(jī)來獲取的。


      二、偽隨機(jī)數(shù)發(fā)生器

          通過程序得到的隨機(jī)數(shù)無論什么算法都一定是通過遞推公式得到的序列,這本身就違反了隨機(jī)的定義,所以它們都不是真正的隨機(jī)數(shù)。偽隨機(jī)數(shù)中一個很重要的概念就是“種子”,種子決定了隨機(jī)數(shù)的固定序列,例如在C語言rand函數(shù)得到的序列每次都是相同的,如果想得到不同序列需要調(diào)用srand設(shè)置種子;同理在Java中 new Random(1)的構(gòu)造函數(shù)參數(shù)來設(shè)置種子。下面介紹生成PRNG的幾種常見方法:

      1.取中法:


      i.平方取中法:

      這個方法是由馮·諾伊曼在1946年提出的,思想很簡單:

      選擇一個m位數(shù)Ni作為種子,做平方運(yùn)算(記為Ni+ 1 = (Ni * Ni)...),結(jié)果若不足2m個位,在前補(bǔ)0。在這個數(shù)選中間m個位的數(shù)作為Ni+1。這個算法明顯又很大弊端,不僅周期短而且分布不均勻,比如10000平方取中結(jié)果就一直為00000了。
      示例代碼:
      [java] view plain copy
      1. public class CustomRandom {  
      2.       
      3.     static final int FIGURES = 10000;  
      4.     static long mRandom;  
      5.       
      6.     public static void main(String[] args) {  
      7.         long seed = System.currentTimeMillis();  
      8.         mRandom = seed % FIGURES;  
      9.         for (int i = 0; i < 10; i++)  
      10.             System.out.println(getRandom(seed));  
      11.     }  
      12.   
      13.     private static long getRandom(long seed) {  
      14.         return mRandom = (mRandom * mRandom / (long) Math.pow(105/2)) % FIGURES;  
      15.     }  
      16. }  

      ii:常數(shù)取中法

      此方法與平方取中法稍有不同,只是把一個隨機(jī)數(shù)的平方換成了隨機(jī)數(shù)與常數(shù)的乘積(記為Ni+1 = (K * Ni)...),對于隨機(jī)分布等沒有什么提升。

      iii:乘法取中法:

      此方法是對平方取中法的一定優(yōu)化,公式記為Ni+1 = (Ni * Ni-1)...

      2.同余法

      同余是啥不知道的同學(xué)見我《素性測試》中的wilson檢測中有解釋
      同余法是大部分變成語言的RNG所采用的算法,線性同余方程為:Ni+1  = a Ni + C (mod m),其中a為乘子,C為增量,m為膜。產(chǎn)生的隨機(jī)序列Rn = Ni / m。
      當(dāng) a = 1 并且 C != 0時,此同余法稱為加法同余法
      當(dāng)a != 1 并且 C = 0時,此同余法稱為乘法同余法
      當(dāng)a != 1 并且 C != 0時,此同余法稱為混合同余法
      同余法當(dāng)m越大,Ni的范圍也就越大,隨機(jī)分布的也就越均勻,Rn也就分布的更均勻,所以m取值應(yīng)盡可能的大,充分利用計(jì)算機(jī)字長。對于如何獲得滿周期隨機(jī)數(shù)是存在判定定理的,當(dāng)且僅當(dāng)滿足下列條件時,踐行同余法是滿周期的:
      1.C與m互質(zhì)
      2.對于m的每一個質(zhì)因子p,(a-1)為p的倍數(shù)
      3.若m可被4整除, (a-1)也可被4整除。
      示例代碼:
      [java] view plain copy
      1. public class CustomRandom {  
      2.       
      3.     static final int A = 3;  
      4.     static final int M = (1 << 31) - 1 ;  
      5.       
      6.     private static long mRandom;  
      7.       
      8.     public static void main(String[] args) {  
      9.         mRandom = System.currentTimeMillis() / Integer.MAX_VALUE;  
      10.         for (int i = 0; i < 10; i++) {  
      11.             mRandom = (mRandom * A) % M;  
      12.             System.out.println(mRandom);  
      13.         }  
      14.     }  
      15. }  
      除此之外還有二次同余,三次同余等,原理差不多。

      3.移位法:

      由于計(jì)算機(jī)特有的邏輯移位運(yùn)算,可以對種子N0左移n位得到M1,右移n位得到M2,將M1與M2做邏輯相加運(yùn)算得到隨機(jī)數(shù)N1,
      公式為Ni+1 = Ni  >> n + Ni << n.移位法速度非常快,但對初始值要求較高,很難得到滿意的隨機(jī)序列。
      示例代碼:
      [java] view plain copy
      1. public class CustomRandom {  
      2.       
      3.     static final int N = 5;  
      4.     static long mRandom;  
      5.       
      6.     public static void main(String[] args) {  
      7.         long mRandom = System.currentTimeMillis();  
      8.         for (int i = 0; i < 10; i++) {  
      9.             mRandom = Math.abs((mRandom >> N) + (mRandom << N));  
      10.             System.out.println(mRandom);  
      11.         }  
      12.     }  
      13. }  

      4.梅森旋轉(zhuǎn)算法

      梅森旋轉(zhuǎn)算法是當(dāng)今生成隨機(jī)數(shù)質(zhì)量最好的算法,如php,python,perl等流行編程語言內(nèi)置的PRNG都是采用該算法實(shí)現(xiàn)。

      下面是來至wiki的介紹:

      梅森旋轉(zhuǎn)算法(Mersenne twister)是一個偽隨機(jī)數(shù)生成算法。由松本真和西村拓士在1997年開發(fā),基于有限二進(jìn)制字段上的矩陣線性地鬼F_{2}。可以快速產(chǎn)生高質(zhì)量的偽隨機(jī)數(shù), 修正了古典隨機(jī)數(shù)發(fā)生算法的很多缺陷。

      下面的一段偽代碼使用MT19937算法生成范圍在[0, 232 ? 1]的均勻分布的32位整數(shù)

      [plain] view plain copy
      1. <span style="font-size:10px;"> //創(chuàng)建一個長度為624的數(shù)組來存儲發(fā)生器的狀態(tài)</span>  
      2.  int[0..623] MT  
      3.  int index = 0  
      4.    
      5.  //用一個種子初始化發(fā)生器  
      6.  function initialize_generator(int seed) {  
      7.      i := 0  
      8.      MT[0] := seed  
      9.      for i from 1 to 623 { // 遍歷剩下的每個元素  
      10.          MT[i] := last 32 bits of(1812433253 * (MT[i-1] xor (right shift by 30 bits(MT[i-1]))) + i) // 0x6c078965  
      11.      }  
      12.  }  
      13.    
      14.  // Extract a tempered pseudorandom number based on the index-th value,  
      15.  // calling generate_numbers() every 624 numbers  
      16.  function extract_number() {  
      17.      if index == 0 {  
      18.          generate_numbers()  
      19.      }  
      20.    
      21.      int y := MT[index]  
      22.      y := y xor (right shift by 11 bits(y))  
      23.      y := y xor (left shift by 7 bits(y) and (2636928640)) // 0x9d2c5680  
      24.      y := y xor (left shift by 15 bits(y) and (4022730752)) // 0xefc60000  
      25.      y := y xor (right shift by 18 bits(y))  
      26.   
      27.      index := (index + 1) mod 624  
      28.      return y  
      29.  }  
      30.    
      31.  // Generate an array of 624 untempered numbers  
      32.  function generate_numbers() {  
      33.      for i from 0 to 623 {  
      34.          int y := (MT[i] & 0x80000000)                       // bit 31 (32nd bit) of MT[i]  
      35.                         + (MT[(i+1) mod 624] & 0x7fffffff)   // bits 0-30 (first 31 bits) of MT[...]  
      36.          MT[i] := MT[(i + 397) mod 624] xor (right shift by 1 bit(y))  
      37.          if (y mod 2) != 0 { // y is odd  
      38.              MT[i] := MT[i] xor (2567483615) // 0x9908b0df  
      39.          }  
      40.      }  
      41.  }  
      這里有完整的源碼實(shí)現(xiàn):http://www.cs./~sean/research/mersenne/MersenneTwister.java

      當(dāng)然對于隨機(jī)質(zhì)量的好壞我們要的是具有均勻性、獨(dú)立性,周期性好的序列,對于隨機(jī)數(shù)檢測比較簡單的方式可以輸出在一張二維表上,直觀的看出隨機(jī)性的好壞,也可以采取《積分算法》中的蒙特卡洛方法來具體測試隨機(jī)性;詳細(xì)的檢測可以采取x^2檢測,k-s檢測,poker檢測等對隨機(jī)性各個指標(biāo)的具體檢測這里就不細(xì)說了。
          至此我們只討論了無規(guī)則分布和簡單均勻分布,還有像拉普拉斯分布,正態(tài)分布,泊松分布,貝努里分布,高斯分布等高級分布本文就不再討論了;現(xiàn)在我們再回到來頭思考一個問題:世界上真存在真隨機(jī)發(fā)生器嗎?如果存在,假設(shè)時間倒流,再走一邊,中彩票的會是另一個人,還是冥冥之中,自有天意,當(dāng)然這只有上帝知道。

        作者:nash

        本站是提供個人知識管理的網(wǎng)絡(luò)存儲空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點(diǎn)。請注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購買等信息,謹(jǐn)防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請點(diǎn)擊一鍵舉報。
        轉(zhuǎn)藏 分享 獻(xiàn)花(0

        0條評論

        發(fā)表

        請遵守用戶 評論公約

        類似文章 更多