分析rand()和srand()函數的功能

rand()和srand()函數原型:

int?rand(void)?返回一個范圍在 0 到?RAND_MAX?之間的偽隨機數。

void?srand(unsigned int?seed)用來給rand()?設置隨機數發生器,隨機數發生器輸出不同的數值,rand()?就會生成不同的隨機數

1)、在“D:\Keil_v5\ARM\ARMCC\include\stdlib.h”中,有下面的定義:

#ifdef?__USE_ANSI_EXAMPLE_RAND

#define?srand _ANSI_srand

#define?rand _ANSI_rand

#define?RAND_MAX 0x7fff

#else

#define?RAND_MAX 0x7fffffff??/*MDK-ARM默認使用RAND_MAX0x7fffffff*/

#endif

MDK-ARM默認使用RAND_MAX0x7fffffff

2)、在“D:\Keil_v5\ARM\ARMCC\include\time.h”中,有下面的定義:

extern _ARMABI time_t time(time_t * /*timer*/);

但是time沒有具體的函數,因此“srand((unsigned int)time(NULL))”就不能用了。

srand()函數用生成隨機數種子。當我們使用相同的種子時,將生成相同的隨機數序列。為了能rand()函數生成不同的隨機數,可以使用“TIM1的計數器值”作為作為種子值因為“TIM1的計數器值”是不斷變化的,這樣每次運行rand()函數,就可以生成不同的隨機數序列。

3)、測試rand()和srand()函數

void?TIM1_Interrupt_Initializtion(u16 arr,u16 psc);//函數聲明

//定時器1中斷初始化

//APB2時鐘為72MHz

//arr:自動重裝值。

//psc:時鐘預分頻數

//TIM_CKD_DIV1:定時器時鐘 = 輸入頻率

//TIM_CKD_DIV2:定時器時鐘 = 輸入頻率/2

//TIM_CKD_DIV4:定時器時鐘 = 輸入頻率/4

//TIM1溢出時間: arr*psc/72000000/TIM_CKD_DIVx

//TIM1_Interrupt_Initializtion(1000,72);

//當arr=1000,psc=72時,則為1ms,誤差為1us;

void?TIM1_Interrupt_Initializtion(u16 arr,u16 psc)

{

TIM_TimeBaseInitTypeDef ?TIM_TimeBaseStructure;

NVIC_InitTypeDef NVIC_InitStructure;

RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1, ENABLE);

//使能定時器TIM1的APB2外設時鐘

//定時器TIM1初始化

TIM_TimeBaseStructure.TIM_Period = arr-1;

//設置在下一個更新事件裝入活動的自動重裝載寄存器周期的值

TIM_TimeBaseStructure.TIM_Prescaler =psc-1;

//設置用來作為TIMx時鐘頻率除數的預分頻值

TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1;

//設置時鐘分割:TDTS = Tck_tim

//計算公式:arr*psc/72000000/1,當arr=1000,psc=72時,則為1ms,誤差為1us;

TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;

//TIM向上計數模式

TIM_TimeBaseInit(TIM1, &TIM_TimeBaseStructure);

//根據指定的參數初始化TIMx的時間基數單位

? TIM_SetCounter(TIM1,0); ?????????????????????//設置TIM1的計數器值為0;

??TIM_ClearFlag(TIM1, TIM_FLAG_Update); ???????//清除TIM1溢出的待處理標志位

TIM_ClearITPendingBit(TIM1, TIM_IT_Update ); //清除TIM1中斷的待處理位

// TIM_ITConfig(TIM1,TIM_IT_Update,ENABLE ); //允許TIM1溢出產生中斷

/*中斷優先級NVIC設置

NVIC_PriorityGroup_4設置NVIC中斷分組4:表示搶占優先級為4位,取值為0~15,沒有響應優先級,取值為0

NVIC_PriorityGroup_3設置NVIC中斷分組3:表示搶占優先級為3位,取值為0~7,響應優先級只有1位,取值為0~1

NVIC_PriorityGroup_2設置NVIC中斷分組3:表示搶占優先級為2位,取值為0~3,響應優先級只有2位,取值為0~3

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);//設置系統中斷優先級分組4

NVIC_InitStructure.NVIC_IRQChannel = TIM1_UP_IRQn; ?//TIM1中斷

NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 11; ?//設置搶占優先級為11

NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; ?//設置響應優先級為0

NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; ????//IRQ通道被使能

NVIC_Init(&NVIC_InitStructure); //根據NVIC_InitStruct中指定的參數初始化NVIC嵌套向量中斷控制寄存器

*/

TIM_Cmd(TIM1, ENABLE);//使能TIM1外設

}

#include?"stdlib.h"

//rand()和srand()需要包含stdlib.h頭文件

void?Test_rand_And_srand(void)

{

unsigned int?rand_Value;//聲明無符號32位變量rand_Value

unsigned int?ms;//聲明無符號32位變量ms

rand_Value=rand(); //返回一個范圍在0到RAND_MAX之間的偽隨機數

ms=rand_Value%1000+1;//ms為1到1000之間的數

printf("ms=%u\r\n",ms);

}

int?main(void)

{

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);//設置系統中斷優先級分組4

USART1_Serial_Interface_Enable(115200);

printf("\r\nCPU reset\r\n");

????TIM1_Interrupt_Initializtion(1000,72);

//當arr=1000,psc=72時,則為1ms,誤差為1us;

srand( TIM_GetCounter(TIM1) );//使用“TIM1的計數器值”作為作為種子值

??while(1)

??{

Test_rand_And_srand();

??}

}

仿真結果:

3)、在MDK-ARM中,不用srand()設置隨機數發生器,也可以使用rand()得到不同的隨機數。

#include "stm32f10x.h" //使能uint8_t,uint16_t,uint32_t,uint64_t,int8_t,int16_t,int32_t,int64_t
#include "stdio.h"  //getchar(),putchar(),scanf(),printf(),puts(),gets(),sprintf()
#include "USART1.h"
//注意:"USART1.h"要放在 "stdio.h" 包含文件之后,如果這個位置顛倒了,業不能打印浮點數。#include "stdlib.h"
//rand()需要包含stdlib.h頭文件void Test_Rand(void)
{unsigned int rand_Value;//聲明無符號32位變量rand_Valueunsigned int ms;//聲明無符號32位變量msrand_Value=rand(); //返回一個范圍在0到RAND_MAX之間的偽隨機數printf("rand_Value=%u\r\n",rand_Value);ms=rand_Value%1000+1;//ms為1到1000之間的數printf("ms=%u\r\n",ms);
}int main(void){NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);//設置系統中斷優先級分組4USART1_Serial_Interface_Enable(115200);printf("\r\nCPU reset\r\n");while(1){Test_Rand();}
}

?仿真結果如下:

4)、如果在調用rand()前,每次都使用srand()設置一個常數作為種子,就會得到相同的隨機數。

#include "stm32f10x.h" //使能uint8_t,uint16_t,uint32_t,uint64_t,int8_t,int16_t,int32_t,int64_t
#include "stdio.h"  //getchar(),putchar(),scanf(),printf(),puts(),gets(),sprintf()
#include "USART1.h"
//注意:"USART1.h"要放在 "stdio.h" 包含文件之后,如果這個位置顛倒了,業不能打印浮點數。#include "stdlib.h"
//rand()需要包含stdlib.h頭文件void Test_Rand(void)
{unsigned int rand_Value;//聲明無符號32位變量rand_Valueunsigned int ms;//聲明無符號32位變量mssrand(1);rand_Value=rand(); //返回一個范圍在0到RAND_MAX之間的偽隨機數printf("rand_Value=%u\r\n",rand_Value);ms=rand_Value%1000+1;//ms為1到1000之間的數printf("ms=%u\r\n",ms);
}int main(void){NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);//設置系統中斷優先級分組4USART1_Serial_Interface_Enable(115200);printf("\r\nCPU reset\r\n");while(1){Test_Rand();}
}

仿真結果:

5)、?如果在調用rand()前,只用一次srand()設置一個常數作為種子,可以得到不同的隨機數。

#include "stm32f10x.h" //使能uint8_t,uint16_t,uint32_t,uint64_t,int8_t,int16_t,int32_t,int64_t
#include "stdio.h"  //getchar(),putchar(),scanf(),printf(),puts(),gets(),sprintf()
#include "USART1.h"
//注意:"USART1.h"要放在 "stdio.h" 包含文件之后,如果這個位置顛倒了,業不能打印浮點數。#include "stdlib.h"
//rand()需要包含stdlib.h頭文件void Test_Rand(void)
{unsigned int rand_Value;//聲明無符號32位變量rand_Valueunsigned int ms;//聲明無符號32位變量msrand_Value=rand(); //返回一個范圍在0到RAND_MAX之間的偽隨機數printf("rand_Value=%u\r\n",rand_Value);ms=rand_Value%1000+1;//ms為1到1000之間的數printf("ms=%u\r\n",ms);
}int main(void){NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);//設置系統中斷優先級分組4USART1_Serial_Interface_Enable(115200);printf("\r\nCPU reset\r\n");srand(1);while(1){Test_Rand();}
}

仿真結果:

為什么在keil中,會出現這種結果?

在Keil環境中,如果不使用srand()函數,直接調用rand()函數也可以生成隨機數。調用rand()不但可以生成一個新的隨機數,而且也會更新“種子值”。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/904242.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/904242.shtml
英文地址,請注明出處:http://en.pswp.cn/news/904242.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

debuginfo詳解

debuginfo 是 Linux 系統中存儲調試符號和源代碼信息的特殊軟件包,用于分析內核或用戶態程序的崩潰轉儲文件(如 vmcore、coredump)。它在調試復雜問題(如內核崩潰、程序段錯誤)時至關重要。以下是其核心作用、安裝方法…

Python 爬取微店商品列表接口(item_search)的實戰指南

在電商數據分析、市場調研或競品分析中,獲取商品列表信息是常見的需求。微店作為知名的電商平臺,提供了豐富的商品資源和相應的 API 接口。本文將詳細介紹如何使用 Python 爬蟲技術,通過微店的 item_search 接口根據關鍵詞搜索商品列表&#…

【bazel】bazel簡介及簡單使用

文章目錄 1. What is bazel?2. bazel的核心原理2.1 bazel的構建模型2.2 bazel的核心概念2.3 bazel的關鍵特性 3. bazel的使用3.1 劃分項目結構3.2 編寫BUILD文件3.3 bazel常用命令3.4 bazel依賴管理 參考內容 1. What is bazel? bazel是一個開源的構建工具,它基于…

【Mytais系列】Myatis的設計模式

目錄 設計模式 1. 工廠模式(Factory Pattern) 2. 建造者模式(Builder Pattern) 3. 動態代理模式(Dynamic Proxy Pattern) 4. 模板方法模式(Template Method Pattern) 5. 策略模…

【unity游戲開發入門到精通——UGUI】Mask組件實現UGUI遮罩

注意:考慮到UGUI的內容比較多,我將UGUI的內容分開,并全部整合放在【unity游戲開發——UGUI】專欄里,感興趣的小伙伴可以前往逐一查看學習。 文章目錄 前言如何實現UI遮罩1、Mask組件2、實例3、注意 專欄推薦完結 前言 Mask遮罩是…

Github2025-05-04php開源項目日報 Top10

根據Github Trendings的統計,今日(2025-05-04統計)共有10個項目上榜。根據開發語言中項目的數量,匯總情況如下: 開發語言項目數量PHP項目10Shell項目1Vue項目1Java項目1ASP項目1SecLists - 安全測試人員的伴侶 創建周期:4375 天開發語言:PHP協議類型:MIT LicenseStar數量…

MyBatis 一對多與多對一映射詳解教程

一、基礎概念與場景 一對多(One-to-Many) ? 定義:一個父對象包含多個子對象。 例如:一個商品(Goods)對應多個商品詳情(GoodsDetail) ? 實體類表現:父類中包含 List&l…

ChatGPT:重塑人工智能交互范式的破曉之作

2022年11月30日,總部位于舊金山的研究公司OpenAI正式發布了ChatGPT——一款以病毒式傳播速度席卷全球的AI聊天機器人。它不僅能像人類一樣生成內容、回答問題和解決問題,更在推出后的兩個月內吸引了超過1億月活躍用戶,刷新了消費級技術應用的最快采用率紀錄。這一里程碑事件…

在項目中如何對Map List等對象序列化及反序列化

我們知道,在自定義類中,若想完成序列化必須要實現Serializable接口。 那么在實現后如何進行序列化呢? 一.普通對象 序列化: 1.首先我們要定義一個 序列化所需要的工具類 ObjectMapper //定義序列化所需要的工具類 轉化機器…

筆試專題(十五)

文章目錄 排序子序列題解代碼 消減整數題解代碼 最長公共子序列(二)題解代碼 排序子序列 題目鏈接 題解 1. 貪心 模擬 2. 1 2 3 2 2 應該是有兩個排列子序列的,所以i n-1時ret 3. 把水平的位置和上升部分,水平位置和下降部分分為一個排列子序列 代…

Amazon Bedrock Converse API:開啟對話式AI新體驗

Amazon Bedrock Converse API:開啟對話式AI新體驗 前言 在當今人工智能飛速發展的時代,對話式AI已成為眾多應用的核心組成部分。從智能客服到智能助手,對話式AI為用戶帶來了便捷且高效的交互體驗。而Amazon Bedrock Converse API的出現&…

【Springboot知識】Springboot計劃任務Schedule詳解

文章目錄 Spring Boot 定時任務從原理到實現詳解一、核心原理分析1. 架構分層2. 核心組件3. 線程模型 二、基礎實現步驟1. 添加依賴2. 主類配置3. 定時任務類 三、高級配置技巧1. 自定義線程池2. 動態配置參數3. 分布式鎖集成(Redis示例) 四、異常處理機…

MySQL:聯合查詢

目錄 一、笛卡爾積 ?二、內連接 三、外連接 (1)左外連接 (2)右外連接 (3)全外連接 四、自連接 五、子查詢 (1)單行子查詢 (2)多行子查詢 &…

深入理解 Cortex-M3 的內核寄存器組

每個 MCU 開發工程師一定都了解寄存器這個東西,以 STM32 為例,其擁有非常多的外設模塊,如串口、SPI、IIC 等等,如果要使用這些外設,使其按照我們的要求工作,就需要配置這些外設的寄存器,往這些寄…

網絡安全自動化:找準邊界才能筑牢安全防線

數字時代,企業每天要面對成千上萬的網絡攻擊。面對龐大的服務器群、分散的團隊和長期不重啟的設備,很多企業開始思考:哪些安全操作適合交給機器自動處理?哪些必須由人工把關?今天我們就用大白話聊聊這件事。 一、這些事…

C++負載均衡遠程調用學習之負載均衡算法與實現

目錄 01 lars 系統架構回顧 02 lars-lbAgentV0.4-route_lb處理report業務流程 03 lars-lbAgentV0.4-負責均衡判斷參數配置 04 lars-lbAgentV0.4-負載均衡idle節點的失敗率判斷 05 lars-lbAgentV0.4-負載均衡overload節點的成功率判斷 06 lars-lbAgentV0.4-負載均衡上報提交…

領略算法真諦: 多源bfs

嘿,各位技術潮人!好久不見甚是想念。生活就像一場奇妙冒險,而編程就是那把超酷的萬能鑰匙。此刻,陽光灑在鍵盤上,靈感在指尖跳躍,讓我們拋開一切束縛,給平淡日子加點料,注入滿滿的pa…

雷電模擬器-超好用的Windows安卓模擬器

一、雷電模擬器介紹 雷電模擬器是一款功能強大的軟件,它能夠在電腦上模擬出安卓手機系統,讓你可以在電腦上運行各類手機應用及游戲。其采用虛擬安卓手機操作界面,為玩家帶來了獨特的體驗。 (一)強大的兼容性 雷電模擬…

文章三《機器學習基礎概念與框架實踐》

文章3:機器學習基礎概念與框架實踐 ——從理論到代碼,用Scikit-learn構建你的第一個分類模型 一、機器學習基礎理論:三大核心類型 機器學習是人工智能的核心,通過數據讓計算機自動學習規律并做出預測或決策。根據學習方式,可分為三類: 1. 監督學習(Supervised Learni…

腦機接口技術:開啟人類與機器的全新交互時代

在科技飛速發展的今天,人類與機器的交互方式正經歷著前所未有的變革。從最初的鍵盤鼠標,到觸摸屏,再到語音控制,每一次交互方式的升級都極大地提升了用戶體驗和效率。如今,腦機接口(Brain-Computer Interfa…