加权随机数(没有预定义值!)

Weighted random number (without predefined values!)

目前我需要一个函数来提供一个加权的随机数。 它应该在两个 doubles/integers 之间选择一个随机数(例如 4 和 8),而中间的值 (6) 将平均出现,大约是限制器值 4 和 8 的两倍。 如果这只是关于整数,我可以用变量和自定义概率预定义值,但我需要函数给出至少 2 位数字的双精度数(意味着数千个不同的数字)!

我使用的环境是 "Game Maker",它提供各种基本的随机生成器,但不提供加权生成器。

谁能引导我朝着正确的方向前进如何实现这一目标?

提前致谢!

两个独立连续uniform(0,1)的和,U1U2,在0和2之间有一个连续的对称三角形分布。分布的峰值在1并在两端逐渐变细为零。我们可以通过按 2 缩放并添加 4,即 4 + 2*(U1 + U2).

轻松地将其转换为 (4,8) 的范围

但是,您不希望端点处的高度为零,您需要峰高的一半。换句话说,您想要一个位于矩形底面(即均匀)上的三角形,端点的高度为 h,中间的高度为 2h。这让生活变得简单,因为三角形必须在矩形底边上方有一个高度 h 的顶点,并且高度 h 的三角形的面积是具有相同底边和高度的矩形的一半面积 h.因此,你的概率有 2/3 在底部,1/3 在三角形。

结合以上元素可得出以下伪代码算法。如果rnd()是一个函数调用returns连续均匀(0,1)随机数:

define makeValue()
   if rnd() <= 2/3    # Caution, may want to use 2.0/3.0 for many languages
      return 4 + (4 * rnd())
   else
      return 4 + (2 * (rnd() + rnd()))

我使用它计算出一百万个值并绘制了直方图:

如果有人需要在 Game Maker(或其他语言)中将其作为通用函数:

if random(1) <= argument0
   return argument1 + ((argument2-argument1) * random(1))
else
   return argument1 + (((argument2-argument1)/2) * (random(1) + random(1)))

调用如下(类似于标准random_range函数):

val = weight_random_range(FACTOR, FROM, TO)

"FACTOR" 确定整个概率数字中有多少是常数概率的 "base"。例如。上图的2/3。 0 将提供一个完美的三角形,1 将提供一个矩形(无权重)。