码农的世界

实现指定概率的随机事件

2019-08-25  本文已影响0人  QxQx

在开发中,经常遇到一个需求,给一些事件,并指定这些事件出现的概率。例如:A:10%,B:20%, C:30%,D:40%
按照事件的概率随机选择一个其中一个事件。

实现思路:

根据大学概率论所学的知识(啥,概率论课你睡觉了,我也睡觉了。那就我吹你听吧),这是一个典型的均匀分布问题。不扯那些复杂的公式了,我的概率论知识也差不多都还给老师了,直接画图来解释一下。



图中,A,B,C,D四种颜色画出了四个事件出现的概率,也就是在[0,100]数轴上所占的长度。只要我们在[0-100]中取一个随机数,看这个随机数落在A,B,C,D哪个区间中,就取哪个事件。

用代码实现一下,现在主要写golang,先用golang实现一下:

package main

import (
    "fmt"
    "math/rand"
)

func main() {
    b := make(map[uint32]int32)
    b[0] = 10
    b[1] = 20
    b[2] = 30
    b[3] = 40
    h2 := make([]int, 4)
    for x := 0; x < 200000000; x++ {
        r := rand.Int31n(99)
        i, j := int32(0), int32(0)
        for k, v := range b {
            j = i + v - 1
            if r >= i && r <= j {
                h2[k]++
                break
            }
            i += v
        }
    }
    for _, b := range h2 {
        fmt.Print(float32(b)/2000000, " ")
    }
}

顺便统计了一下事件的概率,为了结果更真实一些,循环了2亿次,这个数据量基本可以比较真实的显示随机性了。
运行结果:



结果已经非常接近我们期待的概率了

java版:

import java.util.HashMap;
import java.util.Map;
import java.util.Random;

public class Main {
    public static void main(String[] args) {

        Map<Integer, Integer> m = new HashMap<>();
        m.put(0, 10);
        m.put(1, 20);
        m.put(2, 30);
        m.put(3, 40);
        int[] h2 = new int[4];
        for (int i = 0; i < h2.length; i++) {
            h2[i] = 1;
        }
        Random random = new Random();
        for (int x = 0; x < 200000000; x++) {
            int i = 0;
            int j = 0;
            int r = random.nextInt(99);
            for (Map.Entry<Integer, Integer> entry : m.entrySet()) {
                j = i + entry.getValue() - 1;
                if (r >= i && r <= j) {
                    h2[entry.getKey()]++;
                    break;
                }
                i += entry.getValue();
            }
        }
        for (int i : h2) {
            System.out.printf("%f   ", i / 2000000.0);
        }
    }
}

运行结果也比较接近期待值

上一篇下一篇

猜你喜欢

热点阅读