微信开发运营架构算法设计模式和编程理论程序员

红包算法

2017-01-29  本文已影响0人  LiuDa12

微信红包

初一,一家人聚在一起发红包,便对微信红包算法产生了些兴趣。ps:这里说的是群红包 。

普通红包

首先是普通红包~

普通红包普通红包
简单地说就是金额和个数都是固定的……
直接计数红包个数就行了……

拼手气红包

这个就比较有意思了

拼手气红包拼手气红包
需要考虑的东西就比较多了

思路

思路借鉴于coderroc
添加200元限制

假设有1000元钱,分给十个人。1000/10 = 100元。这是期望值。从0.01到200的区间中(其中200=期望值×2)Random函数抽取一个数,就是第一个人获得红包的大小。假设第一个人获得了150元,那么剩下的850元平均分给9个人,这九个人平均获得红包大小为94元,那么第二个人的红包大小均匀分布于0.01元到188元的区间中,依次类推。如果Random数超过200重新抽取,如果抽取之后下一次Loop中的期望大于200重新抽取。算法可以保证最后一个人至少抽到0.01元。发红包之前计算期望大于200提示单个红包不多于200元

实现

主体逻辑

public static double getRandomMoney(RedPackage _redPackage) {
    // remainSize 剩余的红包数量
    // remainMoney 剩余的钱
    if (_redPackage.remainSize == 1) {
        _redPackage.remainSize--;
        return (double) Math.round(_redPackage.remainMoney * 100) / 100;
    }
    Random r     = new Random();
    double min   = 0.01; //
    double max   = _redPackage.remainMoney / _redPackage.remainSize * 2;
    double money = r.nextDouble() * max;
    money = money <= min ? 0.01: money;
    money = Math.floor(money * 100) / 100;
    _redPackage.remainSize--;
    _redPackage.remainMoney -= money;
    return money;
}

类体

class RedPackage {
    int    remainSize;
    double remainMoney;
}

需要在获取随机数并计算momey值时加入循环,判断money以及下轮期望是否小于200。如果不成立重新获取随机数。成立跳出Loop。
手机打的手懒就不改代码了

顺便

祝大家春节快乐,万事如意。

我的红包我的红包
上一篇 下一篇

猜你喜欢

热点阅读