【教學】『C/C++』利用rand()及srand()產生整數亂數、小數亂數

文章推薦指數: 80 %
投票人數:10人

要產生不重複的亂數有很多方法,最簡單的就是暴力產生,比對過去產生的數字有相同就重新取,但如果數字一多效率就很差,所以建議要去量大的不重複亂 ... 網頁 首頁 PuckBlog Toolbox 2016/03/20 【教學】『C/C++』利用rand()及srand()產生整數亂數、小數亂數、不重複亂數、不均勻機率亂數 一、亂數種子 在C語言中,使用srand()來設定亂數種子,其來源可以是CPU、記憶體、時間等,最常用時間來當亂數種子,打法如下: srand((unsigned)time(NULL)); Note:使用time()函數時須include 只要放在程式一開始的地方,千萬別放在跑亂數的迴圈中,因為CPU執行指令極快速,取的時間種子相差很小,而你取出來的每個數字都會很相近。

不過用取時間種子還有個缺點,當使用者在一秒執行程式數次,因為取時間是以秒為單位,所以會出現很相近的亂數,改善的方式就是將時間再跟其他來源作運算。

例如用PID: srand((unsigned)time(NULL)+getpid()); 二、整數亂數 rand()這個函數會隨機產生0~RAND_MAX的數字,而RAND_MAX為編譯器設定的數字,可以用Printf("%d",RAND_MAX)來查看。

要產生特定範圍的亂數只要先產生0~1的隨機數就可以完成,產生down~up的亂數公式如下: #[down,up]含上界 rand_num=*rand()/RAND_MAX+; #[down,up)不含上界 rand_num=*rand()/(RAND_MAX+1)+; 很多人會用取mod來算亂數,但這樣會有些數字機率較小,相較而言用上述方法就比較好。

例如我要產生15~30之間的數字,也就是[15,30]: rand_num=(30-15)*rand()/(RAND_MAX)+15 下面這個範例程式是產生10個1到100的亂數: #include #include #include intmain(){ intn=10; srand((unsigned)time(NULL)+getpid()); while(n-->0) printf("%d\n",99*rand()/RAND_MAX+1); return0; } 三、小數亂數 將整數亂數的公式改一下就可以實現小數亂數了,如下: #[down,up]含上界 rand_num=*rand()/RAND_MAX+; #[down,up)不含上界 rand_num=*rand()/(RAND_MAX+1.0)+; 例如我要產生-3.0~3.0之間的數字,也就是[-3.0,3.0]: rand_num=(3.0-(-3.0))*rand()/RAND_MAX+(-3.0); 下面這個範例程式是產生10個-5.0到5.0的亂數: #include #include #include intmain(){ intn=10; srand((unsigned)time(NULL)+getpid()); while(n-->0) printf("%lf\n",10.0*rand()/RAND_MAX-5.0); return0; } 四、不重複亂數 要產生不重複的亂數有很多方法,最簡單的就是暴力產生,比對過去產生的數字有相同就重新取,但如果數字一多效率就很差,所以建議要去量大的不重複亂數,可以使用洗牌法來取。

所謂洗牌法就像玩撲克牌一樣,將欲取的亂數放入陣列,再進行洗牌的動作將數字打亂,之後再取出。

下面這個程式是產生30個1到100不重複亂數: #include #include #include #defineSize100 #defineNum30 intmain(){ inti,poker[Size],temp,pos; srand((unsigned)time(NULL)+getpid()); //放入數字 poker[0]=100; for(i=1;i #include #include #defineA11 #defineA25 #defineA310 #defineA4100 #defineA51000 #defineA610000 #defineA788884 #defineTotal100000 intmain(){ intr; srand((unsigned)time(NULL)+getpid()); printf("歡迎來到「不均勻機率抽獎系統」\n"); system("PAUSE"); while(1){ r=(Total-1)*rand()/RAND_MAX+1; if(r==A1) printf("#恭喜獲得「特獎」\n"); elseif(r>A1&&r<=A2+A1) printf("#恭喜獲得「頭獎」\n"); elseif(r>A2+A1&&r<=A3+A2+A1) printf("#恭喜獲得「二獎」\n"); elseif(r>A3+A2+A1&&r<=A4+A3+A2+A1) printf("#恭喜獲得「三獎」\n"); elseif(r>A4+A3+A2+A1&&r<=A5+A4+A3+A2+A1) printf("#恭喜獲得「四獎」\n"); elseif(r>A5+A4+A3+A2+A1&&r<=A6+A5+A4+A3+A2+A1) printf("#恭喜獲得「五獎」\n"); else printf("#恭喜獲得「安慰獎」\n"); system("PAUSE"); } return0; } 歡迎各位分享更好得寫法,有問題也可以一起討論。

發布者: PuckWang 於 3/20/2016 以電子郵件傳送這篇文章BlogThis!分享至Twitter分享至Facebook分享到Pinterest 標籤: Author:Yi-XiangWang, C/C++ 1則留言: Unknown2022年3月18日下午4:18CasinosNearYouinJordan6-reels&12-reels|AirJordanFindyournexthotelstaynearyounewairjordan18stockxinJordan6-reels&12-reels.All-aroundtop-ratedairjordan18stockxgoodsitehotelsfindairjordan18retrovarsityredwithworld-classwherecanyoubuyairjordan18retromenredamenities,24/7jordan18whiteroyalbluesportsCasinoandSpaandCasino.回覆刪除回覆回覆新增留言載入更多… 較新的文章 較舊的文章 首頁 訂閱: 張貼留言(Atom) PuckBlog 線上工具 編碼解碼工具 雜湊產生器 抽獎程式 安全密碼產生器 倒數/計時/碼表時間工具 客製化QRCode產生器 站內搜尋 站長 PuckWang 檢視我的完整簡介 標籤 系統 (5) 拼豆 (4) 故障排除 (2) 食記 (7) 神奇寶貝戰棋大師(ポケモンコマスター) (2) 軟體 (9) 程式共通 (4) 開箱文 (7) 遊記 (1) 遊戲 (9) Android (1) ASUS (2) Author:Chien-YunChang (6) Author:Yi-XiangWang (42) C/C++ (1) Cisco (2) HTML5 (1) KaliLinux (2) Laravel (1) Linux (3) Minecraft (3) N3DS (2) OpenSource (1) PHP (2) Pokemon精靈寶可夢(神奇寶貝) (3) SDN (2) SuperMarioRun超級瑪利歐酷跑 (6) Ubuntu (3) Unity (1) VMware (3) Windows (3) 網誌存檔 ▼  2016 (44) ►  十二月 (6) ►  十月 (2) ►  九月 (2) ►  五月 (4) ►  四月 (8) ▼  三月 (8) 【教學】『C/C++』利用rand()及srand()產生整數亂數、小數亂數、不重複亂數、不均勻機率亂數 【教學】Linux文字編輯器vim實用環境參數說明,語法高亮、自動縮排、顯示行號、語法樣式 【食記】『高雄/楠梓』第一科大內的「鬆餅先生咖啡吧」鬆餅專賣店 【食記】『高雄/楠梓』「豬吉翔手創肉燥」鹹豬肉、肉燥飯及各式套餐與便當 【教學】正規表示式RegularExpression語法規則 【紀錄】自己的筆電自己拆之ASUSG501JW1TBHDD換480GBSSD更換紀錄 【食記】『高雄/三民』高火旁的平價的義大利麵,Pennoni派諾尼義大利麵 【介紹】美光MicronCrucialSSDMomentum技術,加速固態硬碟存取速度 ►  二月 (9) ►  一月 (5) ►  2015 (18) ►  十二月 (6) ►  十一月 (2) ►  十月 (3) ►  九月 (7) 精選文章 【攻略】『關卡3-3』《特殊金幣取得全攻略》SuperMarioRun超級瑪利歐酷跑 《SuperMarioRun超級瑪利歐酷跑》世界3-3特殊金幣位置及取得方法,想要全破的朋友趕快來參考看看喔!文內有影片示範,同時也會附上圖文說明該注意的地方,是個幫助你全破的好幫手。

更多相關攻略,請至 【SuperMarioRun超級瑪利歐酷跑專欄... 訂閱 發表文章 Atom 發表文章 留言 Atom 留言 總網頁瀏覽量 除了有另外說明以外資訊人生IT-Life以創用CC姓名標示-非商業性-相同方式分享4.0國際授權條款釋出。

如有版權問題請聯絡我 站內搜尋



請為這篇文章評分?