产生特定分布的随机数(一):均匀分布和高斯分布

在信号处理领域,获取特定分布的随机信号是一个很常见的需求,这里把均匀分布和高斯分布两种随机信号的生成方法记录一下,权当备忘。

一、首先是均匀分布,一方面均匀分布是最简单的一种情况,其次,均匀分布是后面产生高斯分布的基础。C代码如下:
#include <stdio.h>
#include < stdlib.h >
#include <time.h>
void uniform_generator(short *signals, int length, int *max)
{
  int i, max_val;
      if(! signals) {
          printf("Empty pointer input\n");
      }
      srand((unsigned) time(NULL)); //用时间做种子,每次产生随机数不一样
max_val = max ? RAND_MAX : *max; //RAND_MAX定义在stdlib.h, 其值为2147483647
     for (i=0; i<length; i++) {
  signals[i] = rand() % max_val; //产生0-(max_val-1)的随机数
  }
}

二、接下来是高斯分布。高斯分布放两个方法,第一种是最基础的基于中心极限定理的方法,第二种是非常巧妙的Box-Muller法。代码如下:

1. 中心极限定理法:

#define NSUM 25
void uniform_generator (double *signals, int length, double avg, double sd)
{
       double x = 0;
      int i, j;

      for(i = 0; i < length; i++)   {
        for(j = 0; j < NSUM; j ++) {
 x += (double)rand() / RAND_MAX;
      }
      x -= NSUM / 2.0;
      x /= sqrt(NSUM / 12.0);
            x = avg + (x * sd); //将 x 映射到一个平均值为 m、标准偏差为 sd 的统计量 
signals[i] = x;
}
}

2. Box-Muller
    基本思想: 先得到服从均匀分布的随机数;  然后再将服从均匀分布的随机数转变为服从正态分布。 Box-Muller 是产生随机数的一种方法。Box-Muller 算法隐含的原理非常深奥,但结果却是相当简单。 如果在 (0,1] 值域内有两个一致的随机数字 U1 和 U2, 可以使用以下两个等式中的任一个算出一个正态分布的随机数字 Z:  Z = R * cos( θ ) 或 Z = R * sin( θ )  其中, R = sqrt(-2 * ln(U2)), θ = 2 * π * U1, 正态值 Z 有一个等于 0 的平均值和一个等于 1 的标准偏差,可使用以下等式将 Z 映射到一个平均值为 m、标准偏差为 sd 的统计量 X: X = m + (Z * sd)。
代码如下:
#define PI 3.141592654
double uniform_generator (double *signals, int length, double avg, double sd)
      static double U, V; 
      static int phase = 0
      double z; 
      int i;
      for(i = 0; i < length; i++)   {
             if (phase == 0) {
                   U = rand() / (RAND_MAX + 1 .0); 
                  V = rand() / (RAND_MAX + 1.0); 
                  Z = sqrt(-2.0 * log(U)) * sin(2.0 * PI * V); 
            } else
                    Z = sqrt(-2.0 * log(U)) * cos(2.0 * PI * V); 
            
              phase = 1 - phase; 
           Z = avg + (Z * sd); //将Z 映射到一个平均值为 m、标准偏差为 sd 的统计量 
           signals[i] = Z;
       }
}
  • 0
    点赞
  • 16
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值