C語(yǔ)言中用于產(chǎn)生隨機(jī)數(shù)的函數(shù)使用方法總結(jié)
在UNIX操作系統(tǒng)和window的操作系統(tǒng)上,我們知道有一個(gè)函數(shù)rand,它就是用來產(chǎn)生隨機(jī)數(shù)的函數(shù)API接口,那么它的原理如何實(shí)現(xiàn)?
如果約定a1=f(seed),an+1=f(an),那么可以得到一個(gè)序列a1,a2,a3..an,那么要制作一個(gè)偽隨機(jī)函數(shù)rand,只需要讓它每調(diào)用一次就返回序列的下一個(gè)元素就行。其實(shí)就是相當(dāng)于第1次調(diào)用rand返回a1,第2次返回a2,…,第n次返回an,這樣每次返回的數(shù)值都不一樣,也就是相當(dāng)于隨機(jī)數(shù)了。但是其實(shí)不是真正的隨機(jī)數(shù),真正的隨機(jī)數(shù)是使用物理現(xiàn)象產(chǎn)生的:比如擲錢幣、骰子、轉(zhuǎn)輪、使用電子元件的噪音、核裂變等等。這樣的隨機(jī)數(shù)發(fā)生器叫做物理性隨機(jī)數(shù)發(fā)生器,它們的缺點(diǎn)是技術(shù)要求比較高。那到底什么是隨機(jī)數(shù)呢?
隨機(jī)數(shù):隨機(jī)數(shù)就是每次運(yùn)行代碼的時(shí)候隨機(jī)產(chǎn)生的數(shù),每次產(chǎn)生的數(shù)的值是無(wú)法確定的,返回 0 到 RANDMAX 之間的隨機(jī)整數(shù)值,不包含 RANDMAX 的值,RANDMAX 的范圍最少是在32767之間(int),即雙字節(jié)(16位數(shù))。若用 unsigned int 雙字節(jié)是65535,四字節(jié)是4294967295的整數(shù)范圍。而且 0 到 RANDMAX 每個(gè)數(shù)字被選中的概率是相同的。
原理:產(chǎn)生隨機(jī)數(shù)的原理是根據(jù)一個(gè)值,一般稱為隨機(jī)種子,然后把這個(gè)種子作為參數(shù),經(jīng)過一系列的公式運(yùn)算產(chǎn)生出一個(gè)值,這個(gè)值就是隨機(jī)數(shù)。
在 C 語(yǔ)言當(dāng)中使用隨機(jī)數(shù)要用到 rand 函數(shù)和 srand 函數(shù),
int rand():返回值為隨機(jī)值,參數(shù)為空,通過 rand 函數(shù)就會(huì)產(chǎn)生一個(gè)隨機(jī)數(shù)。
void srand(unsigned int seed):返回值為空, 就是設(shè)置隨機(jī)種子的,當(dāng)我們不設(shè)置隨機(jī)種子的時(shí)候,默認(rèn)設(shè)置的種子為 1,也就是srand(1)。
使用:
#include<stdlib.h>//得引入 stdlib.h 這個(gè)頭文件
int main()
{
int rand_num = rand();
printf("rand_num = %d\n", rand_num);
return 0;
}
每次運(yùn)行的結(jié)果都一樣,這是為什么呢?上面已經(jīng)說了,隨機(jī)數(shù)產(chǎn)生的是有一個(gè)隨機(jī)種子作為參數(shù),然后返回一個(gè)值,而且默認(rèn)的隨機(jī)種子為1,所以每次產(chǎn)生的隨機(jī)數(shù)都一樣。
如果我們修改一下隨機(jī)種子,會(huì)發(fā)現(xiàn)隨機(jī)數(shù)和原來的不一樣了,但是每次運(yùn)行的結(jié)果還是一樣:
#include<stdlib.h>//得引入 stdlib.h 這個(gè)頭文件
int main()
{
srand(3);
int rand_num = rand();
printf("rand_num = %d\n", rand_num);
srand(5);
rand_num = rand();
printf("rand_num = %d\n", rand_num);
return 0;
}
兩次的輸出結(jié)果不一樣,我的輸出結(jié)果如下:
rand_num = 50421 rand_num = 847425747
但是我們程序肯定是寫好之后,不改動(dòng)隨機(jī)種子,然后每次產(chǎn)生不同的值才對(duì)啊,那我們來如何做呢?既然產(chǎn)生的隨機(jī)值與種子有關(guān),只要每次的隨機(jī)種子不一樣,那么產(chǎn)生的隨機(jī)值也不一樣,我們就可以把時(shí)間作為隨機(jī)種子,因?yàn)槊看芜\(yùn)行時(shí),時(shí)間都不一樣,因此產(chǎn)生的隨機(jī)值也不一樣,因此我們可以這樣:
#include<time.h> //使用 time 函數(shù)必須引入 time.h 頭文件
#include<stdlib.h>
int main()
{
srand((int)time(0));
int rand_num = rand();
printf("rand_num = %d\n", rand_num);
return 0;
}
這樣的話,每次輸出結(jié)果都不一樣了。
通過上面的方法,我們可以獲取不同的隨機(jī)值了,但是我們一般會(huì)獲取一定范圍內(nèi)的隨機(jī)值,比如返回 0~100 之間的返回值,比如模擬骰子,隨機(jī)返回 1~6 的值。那么我們?cè)撊绾巫瞿兀?/p>
我們要返回 0~6 的隨機(jī)值,只需在上面返回隨機(jī)值的地方對(duì) 7 取余即可:
int rand_num = rand() % 7;
printf("rand_num = %d\n", rand_num);
所以我們?nèi)绻祷?0~a 的隨機(jī)值,只要對(duì) a + 1 取余即可,所以有下面的公式:
int rand_num = rand() % (a + 1);//返回 0 ~ a 的隨機(jī)值
如果我們要返回 a ~ b 的隨機(jī)值,公式是什么呢?因?yàn)殡S機(jī)數(shù)取余法只能返回 0 到某個(gè)數(shù)的隨機(jī)值,所以 a ~ b 的隨機(jī)值,我們可以先返回 0 ~ (b – a)的隨機(jī)值,然后再加上 a 即可:
int rand_num = rand() % (b - a + 1);//1、返回 0 ~ (b - a)的隨機(jī)值 rand_num = rand_num + a; //2、返回 a ~ b 的隨機(jī)值
因此上面的 1 和 2 合并之后的公式為:
int rand_num = rand() % (b - a + 1) + a;//返回 a ~ b 的隨機(jī)值
大家現(xiàn)在做這樣的操作:
#include<stdlib.h>
int main()
{
srand(2);//隨機(jī)種子固定為2
for(int i = 0; i < 5; i++)
{
int rand_num = rand();
printf("rand_num = %d\n", rand_num);//注意輸出結(jié)果
}
return 0;
}
既然隨機(jī)種子一樣,為什么輸出結(jié)果不一樣呢?這里得注意一下,如果程序沒有結(jié)束,而且也沒有重新設(shè)置過隨機(jī)種子,那么系統(tǒng)會(huì)把上次的隨機(jī)值作為下次隨機(jī)函數(shù)的隨機(jī)種子,因此在上面的 for 循環(huán)當(dāng)中,其實(shí)每次的循環(huán)種子都不一樣,怎么驗(yàn)證呢?先看我這里的輸出結(jié)果為:
rand_num = 33614 rand_num = 564950498 rand_num = 1097816499 rand_num = 1969887316 rand_num = 140734213
我們可以把隨機(jī)種子設(shè)置成其中的一個(gè) rand_num 值,比如 33614,那么輸出結(jié)果如果為 564950498 的話,那么說明在 for 循環(huán)中每次都把隨機(jī)值作為下次的隨機(jī)函數(shù)的隨機(jī)種子了。
srand(33614);
int rand_num = rand();
printf("rand_num = %d\n", rand_num);
結(jié)果:
rand_num = 564950498;
驗(yàn)證完畢。
arc4random() 函數(shù):
這個(gè)函數(shù)是 C 語(yǔ)言封裝的一個(gè)比較智能的隨機(jī)函數(shù),我們只要調(diào)用這個(gè)函數(shù),就會(huì)產(chǎn)生隨機(jī)數(shù),不用設(shè)置隨機(jī)種子,而且用法很簡(jiǎn)單:
int arc_rand = arc4random();
printf("arc_rand = %d\n", arc_rand);
每次的運(yùn)行結(jié)果都不一樣。如果要產(chǎn)生 a ~ b 的隨機(jī)值,公式也是:
arc4random() % (b - a + 1) + a;
上一篇:C語(yǔ)言中交換int型變量的值及轉(zhuǎn)換為字符數(shù)組的方法
欄 目:C語(yǔ)言
下一篇:C++實(shí)現(xiàn)簡(jiǎn)單的HTTP服務(wù)器
本文標(biāo)題:C語(yǔ)言中用于產(chǎn)生隨機(jī)數(shù)的函數(shù)使用方法總結(jié)
本文地址:http://www.jygsgssxh.com/a1/Cyuyan/2348.html
您可能感興趣的文章
- 04-02c語(yǔ)言函數(shù)調(diào)用后清空內(nèi)存 c語(yǔ)言調(diào)用函數(shù)刪除字符
- 04-02c語(yǔ)言的正則匹配函數(shù) c語(yǔ)言正則表達(dá)式函數(shù)庫(kù)
- 04-02func函數(shù)+在C語(yǔ)言 func函數(shù)在c語(yǔ)言中
- 04-02c語(yǔ)言中對(duì)數(shù)函數(shù)的表達(dá)式 c語(yǔ)言中對(duì)數(shù)怎么表達(dá)
- 04-02c語(yǔ)言用函數(shù)寫分段 用c語(yǔ)言表示分段函數(shù)
- 04-02c語(yǔ)言編寫函數(shù)冒泡排序 c語(yǔ)言冒泡排序法函數(shù)
- 04-02c語(yǔ)言沒有round函數(shù) round c語(yǔ)言
- 04-02c語(yǔ)言分段函數(shù)怎么求 用c語(yǔ)言求分段函數(shù)
- 04-02C語(yǔ)言中怎么打出三角函數(shù) c語(yǔ)言中怎么打出三角函數(shù)的值
- 04-02c語(yǔ)言調(diào)用函數(shù)求fibo C語(yǔ)言調(diào)用函數(shù)求階乘


閱讀排行
- 1C語(yǔ)言 while語(yǔ)句的用法詳解
- 2java 實(shí)現(xiàn)簡(jiǎn)單圣誕樹的示例代碼(圣誕
- 3利用C語(yǔ)言實(shí)現(xiàn)“百馬百擔(dān)”問題方法
- 4C語(yǔ)言中計(jì)算正弦的相關(guān)函數(shù)總結(jié)
- 5c語(yǔ)言計(jì)算三角形面積代碼
- 6什么是 WSH(腳本宿主)的詳細(xì)解釋
- 7C++ 中隨機(jī)函數(shù)random函數(shù)的使用方法
- 8正則表達(dá)式匹配各種特殊字符
- 9C語(yǔ)言十進(jìn)制轉(zhuǎn)二進(jìn)制代碼實(shí)例
- 10C語(yǔ)言查找數(shù)組里數(shù)字重復(fù)次數(shù)的方法
本欄相關(guān)
- 04-02c語(yǔ)言函數(shù)調(diào)用后清空內(nèi)存 c語(yǔ)言調(diào)用
- 04-02func函數(shù)+在C語(yǔ)言 func函數(shù)在c語(yǔ)言中
- 04-02c語(yǔ)言的正則匹配函數(shù) c語(yǔ)言正則表達(dá)
- 04-02c語(yǔ)言用函數(shù)寫分段 用c語(yǔ)言表示分段
- 04-02c語(yǔ)言中對(duì)數(shù)函數(shù)的表達(dá)式 c語(yǔ)言中對(duì)
- 04-02c語(yǔ)言編寫函數(shù)冒泡排序 c語(yǔ)言冒泡排
- 04-02c語(yǔ)言沒有round函數(shù) round c語(yǔ)言
- 04-02c語(yǔ)言分段函數(shù)怎么求 用c語(yǔ)言求分段
- 04-02C語(yǔ)言中怎么打出三角函數(shù) c語(yǔ)言中怎
- 04-02c語(yǔ)言調(diào)用函數(shù)求fibo C語(yǔ)言調(diào)用函數(shù)求
隨機(jī)閱讀
- 08-05DEDE織夢(mèng)data目錄下的sessions文件夾有什
- 08-05織夢(mèng)dedecms什么時(shí)候用欄目交叉功能?
- 08-05dedecms(織夢(mèng))副欄目數(shù)量限制代碼修改
- 04-02jquery與jsp,用jquery
- 01-11Mac OSX 打開原生自帶讀寫NTFS功能(圖文
- 01-10使用C語(yǔ)言求解撲克牌的順子及n個(gè)骰子
- 01-11ajax實(shí)現(xiàn)頁(yè)面的局部加載
- 01-10SublimeText編譯C開發(fā)環(huán)境設(shè)置
- 01-10delphi制作wav文件的方法
- 01-10C#中split用法實(shí)例總結(jié)


