#申请原创#@21小跑堂
一、实际项目中,经常需要产生一些符合某某分布的随机数,如(服从均匀分布的随机数、服从柯西分布的随机数等);
二、GD32F450本身自带的真随机数发生器是通过连续模拟噪声生成一个 32 位的随机数值,但无法确定服从什么分布;另一方面不带真随机数发生器的单片机也有很多。
三、通过ADC采集随机噪声作为随机数同自带的真随机数发生器一样,无法确定噪声服从是满分布;综上所述,需要产生服从某某分布的随机数需要从算法进行解决。关键对带不带真随机数发生器的单片机都可以适用
四、服从均匀分布随机数
//均匀分布
double uniform(double a,double b,long int * seed)
{
double t;
* seed=2045*(*seed)+1;
* seed=*seed-(*seed/1048576)*1048576;
t=(*seed)/1048576.0;
t=a+(b-a)*t;
return t;
}
五、服从高斯分布(正态分布)的随机数
//高斯(正态)分布
double guass(double mean,double sigma,long int *seed)
{
int i;
double x,y;
for (x=0,i=0;i<12;i++)
{
x+=uniform(0.0,1.0,seed);
}
x-=6.0;
y=mean+x*sigma;
return y;
}
六、服从指数分布的随机数生成
//指数分布
double exponent(double beta,long int *seed)
{
double u,x;
u=uniform(0.0,1.0,seed);
x=-beta*log(u);
return x;
}
七、服从拉普拉斯分布的随机数
//拉普拉斯分布
double laplace(double beta,long int *seed)
{
double u1,u2,x;
u1=uniform(0.0,1.0,seed);
u2=uniform(0.0,1.0,seed);
if(u1<0.5)
{
x=-beta*log(1.0-u2);
}
else
{
x=beta*log(u2);
}
return x;
}
八、服从瑞利分布的随机数生成
//瑞利分布
double rayleigh(double sigma,long int *seed)
{
double u,x;
u=uniform(0.0,1.0,seed);
x=-2.0*log(u);
x=sigma*sqrt(x);
return x;
}
九、服从对数正态分布的随机数生成
//对数-正态分布
double logform(double u,double sigma,long int *seed)
{
double x,y;
y=guass(u,sigma,seed);
x=exp(y);
return x;
}
十、服从柯西分布的随机数生成
//柯西分布
double cauchy(double a,double b,long int *seed)
{
double u,x;
u=uniform(0.0,1.0,seed);
x=a-b/tan(3.1492653*u);
return x;
}
十一、服从韦伯分布的随机数生成
//韦伯分布
double weibull(double a,double b,long int *seed)
{
double u,x;
u=uniform(0.0,1.0,seed);
u=-log(u);
x=b*pow(u,1.0/a);
return x;
}
十二、服从埃尔朗分布的随机数生成
//埃尔朗分布
double erlang(int m,double beta,long int *seed)
{
int i;
double u,x;
for(u=1.0,i=1;i<m;i++)
{
u*=uniform(0.0,1.0,seed);
}
x=-beta*log(u);
return x;
}
十三、服从伯努利分布的随机数生成
//伯努利分布
int bn(double p,long int *seed)
{
int x;
double u;
u=uniform(0.0,1.0,seed);
x=(u<p)?1:0;
return x;
}
十四、服从伯努利-高斯分布的随机数生成
//伯努利-高斯分布
double bn_gauss(double p,double mean,double sigma,long int *seed)
{
double u,x;
u=uniform(0.0,1.0,seed);
if(u<p)
{
x=guass(mean,sigma,seed);
}
else
{
x=0.0;
}
return x;
}
十五、服从二项式分布的随机数生成
//二项式分布
int bin_(int n,double p,long int *seed)
{
int i;
int x;
for(x=0,i=0;i<n;i++)
{
x+=bn(p,seed);
}
return x;
}
十六、服从泊松分布的随机数生成
//泊松分布
int poisson(double lamuda,long int *seed)
{
int i=0,x;
double a,b=1.0,u;
a=exp(-lamuda);
do
{
u=uniform(0.0,1.0,seed);
b*=u;
i++;
}while(b>=a);
x=i-1;
return x;
}
十七、测试平台:GD32F450ZiT6
十八、测试主函数
/*!
\file main.c
\brief design by 张恩寿
\version 2021-08-15, V1.0.0, SDK for keria
*/
/*
昆明电器科学研究所.
*/
#include "usart.h"
#include "systick.h"
#include "led.h"
#include "key.h"
#include "eeprom.h"
#include "rng.h"
u16 mem_size[2]={0};
u32 uid[3]={0};
static void rng_uniform_test(void)
{
double a,b,x;
int i,j;
long int s;
a=0.0;
b=1.0;
s=13579;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=uniform(a,b,&s);
printf("%13.7f",x);
}
printf("\r\n");
}
}
static void rng_guass_test(void)
{
int i,j;
long int s=13579;
double mean=0.0;
double sigma=1.0;
double x;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=guass(mean,sigma,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_exponent_test(void)
{
int i,j;
long int s=13579;
double x;
double beta=2.0;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=exponent(beta,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_laplace_test(void)
{
int i,j;
long int s=13579;
double x,beta=1.5;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=laplace(beta,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_rayleigh_test(void)
{
int i,j;
long int s=13579;
double x,sigma=1.0;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=rayleigh(sigma,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_logform_test(void)
{
int i,j;
long int s=13579;
double x,u=0.0,sigma=0.5;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=logform(u,sigma,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_cauchy_test(void)
{
int i,j;
long int s=13579;
double x,a=1.0,b=1.0;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=cauchy(a,b,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_weibull_test(void)
{
int i,j;
long int s=13579;
double x,a=2.0,b=1.0;
for(i=0;i<10;i++)
{
for (j=0;j<5;j++)
{
x=weibull(a,b,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_erlang_test(void)
{
int i,j,m=3;
double x,beta=1.0;
long int s=13579;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=erlang(m,beta,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_bn_test(void)
{
int i,j,x;
long int s=13579;
double p=0.7;
for (i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=bn(p,&s);
printf("%11d",x);
}
printf("\r\n");
}
}
static void rng_bn_gauss_test(void)
{
int i,j;
long int s=13579;
double x,p=0.4,mean=0.0,sigma=1;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=bn_gauss(p,mean,sigma,&s);
printf("%13.7lf",x);
}
printf("\r\n");
}
}
static void rng_bin__test(void)
{
int i,j,n=5,x;
long int s=13579;
double p=0.7;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=bin_(n,p,&s);
printf("%11d",x);
}
printf("\r\n");
}
}
static void rng_poisson_test(void)
{
int i,j,x;
long int s=13579;
double n=4.0;
for(i=0;i<10;i++)
{
for(j=0;j<5;j++)
{
x=poisson(n,&s);
printf("%11d",x);
}
printf("\r\n");
}
}
int main(void)
{
nvic_priority_group_set(NVIC_PRIGROUP_PRE2_SUB2);
systick_set(200);
eeprom_io_set();
usart_config(115200);
mem_size[0]=mem_size_get(mem_flash);
mem_size[1]=mem_size_get(mem_sram);
get_cpu_uid(uid);
led_set();
key_set();
printf("welcome to use platform of GD32F450\r\n");
printf("cpu flash size:%d,sram size:%d\r\n",mem_size[0],mem_size[1]);
printf("cpu uid code:0X%X%X%X\r\n",uid[0],uid[1],uid[2]);
eeprom_write_byte(0,241);
eeprom_wait_standby_state();
printf("%d\r\n",eeprom_read_byte(0));
eeprom_write_u16(1,565);
printf("%d\r\n",eeprom_read_u16(1));
eeprom_write_int(3,-3000);
printf("%d\r\n",eeprom_read_int(3));
eeprom_write_u32(7,3000);
printf("%d\r\n",eeprom_read_u32(7));
eeprom_write_float(11,5.214);
printf("%f\r\n",eeprom_read_float(11));
printf("\r\n");
printf("服从均匀分布随机数测试:\r\n");
rng_uniform_test();
printf("\r\n");
printf("服从正态分布随机数测试:\r\n");
rng_guass_test();
printf("\r\n");
printf("服从指数分布随机数测试:\r\n");
rng_exponent_test();
printf("\r\n");
printf("服从拉普拉斯分布随机数测试:\r\n");
rng_laplace_test();
printf("\r\n");
printf("服从瑞利分布随机数测试:\r\n");
rng_rayleigh_test();
printf("\r\n");
printf("服从对数-正态分布随机数测试:\r\n");
rng_logform_test();
printf("\r\n");
printf("服从柯西分布随机数测试:\r\n");
rng_cauchy_test();
printf("\r\n");
printf("服从韦伯分布随机数测试:\r\n");
rng_weibull_test();
printf("\r\n");
printf("服从埃尔朗分布随机数测试:\r\n");
rng_erlang_test();
printf("\r\n");
printf("服从伯努利分布随机数测试:\r\n");
rng_bn_test();
printf("\r\n");
printf("服从伯努利-高斯分布随机数测试:\r\n");
rng_bn_gauss_test();
printf("\r\n");
printf("服从二项式分布随机数测试:\r\n");
rng_bin__test();
printf("\r\n");
printf("服从泊松分布随机数测试:\r\n");
rng_poisson_test();
while (1)
{
led=!led;
delay_ms(1000);
}
}
十九、工程文件
|
共1人点赞
|