红包算法分析

有人认为,抢红包的额度是从0.01到剩余平均值*N(N是一个系数,决定最大的红包值)之间,比如一共发了10块钱,发了10个红包:第一个人可以拿到(0.01~1*N)之间的一个红包值,当然为了确保所有人至少有1分钱拿,不能前几个人就把钱拿光了,因此需要有一个判断算法。举个例子,如果每个人都拿了自己的最大值:

package 红包分配;

public class test {
public static void main(String[] args){
float num=10,N=1.9f;
int people=10;
for(int i=0;i<10;i++)
{
System.out.println("the number"+people+"can get "+num/people*N);
num=num-num/people*N;
people--;
}
System.out.println("there remain"+num);
} }

运行结果如下:

the number10can get 1.9
the number9can get 1.71
the number8can get 1.5176251
the number7can get 1.3225019
the number6can get 1.1241267
the number5can get 0.9217838
the number4can get 0.71438247
the number3can get 0.5000677
the number2can get 0.2750373
the number1can get 0.027503723
there remain-0.01302808

最终剩余的钱数为负数,不符合要求,所以说基数的选取是非常重要的。

设置金额的限额

private static final float MINMONEY = 0.01f;
private static final float MAXMONEY = 200f;

红包的最小额度是0.01元,最大额度是200元。

判断金额是否合法

如果金额超过限额,就出错了

private boolean isRight(float money,int count)
{
double avg = money/count;
if(avg<MINMONEY){
return false;
}
else if(avg>MAXMONEY)
{
return false;
}
return true;
}

随机产生红包

用随机方法产生一个在最大值和最小值之间的一个红包,并判断该红包是否合法,是否在产生这个红包之后红包金额变成负数。另外,在这次产生红包值较小时,下一次就产生一个大一点的红包。

private float randomRedPacket(float money,float mins,float maxs,int count)
{
if(count==1)
{
return (float)(Math.round(money*100))/100;
}
if(mins == maxs)
{
return mins;//如果最大值和最小值一样,就返回mins
}
float max = maxs>money?money:maxs;
float one = ((float)Math.random()*(max-mins)+mins);
one = (float)(Math.round(one*100))/100;
float moneyOther = money - one;
if(isRight(moneyOther,count-1))
{
return one;
}
else{
//重新分配
float avg = moneyOther / (count-1);
if(avg<MINMONEY)
{
return randomRedPacket(money,mins,one,count);
}else if(avg>MAXMONEY)
{
return randomRedPacket(money,one,maxs,count);
}
}
return one;
}

实现红包分配

为了避免一个红包占用大量的资金,设定非最后一个红包的最大金额,可以设置为平均值的N倍,基于前面的方法就可以实现红包的分配了。

private static final float TIMES = 2.1f;

public List<Integer> splitRedPackets(float money,int count)
{
if(!isRight(money,count))
{
return null;
}
List<Float> list = new ArrayList<Float>();
float max = (float)(money*TIMES/count); max = max>MAXMONEY?MAXMONEY:max;
for(int i=0;i<count;i++)
{
float one = randomRedPacket(money,MINMONEY,max,count-i);
list.add(one);
money-=one;
}
return list;
}
private static final float TIMES = 2.1f;

public List<Integer> splitRedPackets(float money,int count)
{
if(!isRight(money,count))
{
return null;
}
List<Float> list = new ArrayList<Float>();
float max = (float)(money*TIMES/count); max = max>MAXMONEY?MAXMONEY:max;
for(int i=0;i<count;i++)
{
float one = randomRedPacket(money,MINMONEY,max,count-i);
list.add(one);
money-=one;
}
return list;
}

编写主函数

 public static void main(String[] args) {
RedPacketUtil util = new RedPacketUtil();
System.out.println(util.splitRedPackets(200, 100));
}

java实现微信红包分配算法的更多相关文章

  1. 研究微信红包分配算法之Golang版

    今天来看一下红包的分配,参考几年前流传的微信红包分配算法,今天用Golang实现一版,并测试验证结果. 微信红包的随机算法是怎样实现的?https://www.zhihu.com/question/2 ...

  2. PHP用抛物线的模型实现微信红包生成算法的程序源码

    <?php /* *Author:Kermit *Time:2015-8-26 *Note:红包生成随机算法 */ header("Content-type:text/html;cha ...

  3. PHP微信红包生成算法的程序源码(用抛物线的模型实现)

    代码如下: <?php /* * 红包生成随机算法 */ header("Content-type:text/html;charset=utf-8"); date_defau ...

  4. PHP微信红包的算法实现探讨

    header("Content-Type: text/html;charset=utf-8");//输出不乱码,你懂的 $total=10;//红包总额 $num=8;// 分成8 ...

  5. PHP实现微信随机红包算法和微信红包的架构设计简介

    微信红包的架构设计简介: 原文:https://www.zybuluo.com/yulin718/note/93148 @来源于QCon某高可用架构群整理,整理朱玉华. 背景:有某个朋友在朋友圈咨询微 ...

  6. PHP实现微信红包算法和微信红包的架构设计简介

    微信红包的架构设计简介: 原文:https://www.zybuluo.com/yulin718/note/93148 @来源于QCon某高可用架构群整理,整理朱玉华. 背景:有某个朋友在朋友圈咨询微 ...

  7. 如何用 js 实现一个类似微信红包的随机算法

    如何用 js 实现一个类似微信红包的随机算法 js, 微信红包, 随机算法 "use strict"; /** * * @author xgqfrms * @license MIT ...

  8. java 微信红包算法代码实现及架构设计

    转载至:https://www.zybuluo.com/yulin718/note/93148 微信红包的架构设计简介 架构 @来源于QCon某高可用架构群整理,整理朱玉华. 背景:有某个朋友在朋友圈 ...

  9. java实现红包的分配算法

    个人推测,微信红包在发出的时候已经分配好金额.比如一个10元的红包发给甲乙丙三个人,其实在红包发出去的时候,已经确定了第一个会领取多少,第二个会领取多少金额. 而不是在领取的时候才计算的.下面贴出实现 ...

随机推荐

  1. 谷歌YSlow准则

    谷歌YSlow准则 YSlow可以对网站的页面进行分析,并告诉你为了提高网站性能,如何基于某些规则而进行优化. 测试个人站点 通过测试个人站点可以获得下面的数据 23条准则 Make fewer HT ...

  2. wpf后置代码中的Grid布局以及图片路径的设置

    之前用Grid练习连连看布局时,遇到了几个困惑.此次就把当时的一些收获写出来,供以后翻看. 图片路径可能比较常用,所以就写在第一个了. 在xaml中,设置图片非常简单,只要把图片拷贝到资源目录(这里假 ...

  3. CREELINKS平台_处理器CeGpio资源使用说明(CeGpio的配置与使用)

    0x00 CREELINKS平台简介     CREELINKS(创e联)是由大信科技有限公司研发,集合软硬件.操作系统.数据云储存.开发工具于一体,用于物联网产品的设计.研发与生产的平台.    平 ...

  4. VS2008 + WDK 配置 及其编译错误

    VS2008 + SP1 + Win7 X64 1. 安装WDK,并配置系统环境变量:WDKROOT-D:\WinDDK\7600.16385.1 2. 启动VS2005,在菜单栏“工具”-“选项”内 ...

  5. BZOJ [HAOI2011]防线修建(动态凸包)

    听说有一种很高端的东西叫动态凸包维护dp就像学一下,不过介于本人还不会动态凸包就去学了下,还是挺神奇的说,维护上下凸包的写法虽然打得有点多不过也只是维护复制黏贴的事情而已罢了. 先说下动态凸包怎么写吧 ...

  6. es6的解构赋值学习(1)

    相对es5的简单的"="赋值来说,es6增加了一种新的赋值模式--解构赋值,按照它的规则,可以从数组和对象中提取值来对变量进行赋值,个人觉得方便了很多,但是这个模式有点恶心人,相比 ...

  7. 最常用的UML工具介绍

    最常用的UML工具介绍 1.Rational Rose.大名鼎鼎,史上最有名.最无可替代的UML产品,以至于,大多数将之等同于UML工具,正如将可乐等同于可口可乐.需要指出的是,自从 Rational ...

  8. stm32 复位后 引起引脚的变化,输出电平引起的问题

    在做项目的时候,需要通过蓝牙发送指令给STM32,使其复位,然后进入bootloader程序进行升级,但是复位后会导致蓝牙模块关机.stm32有个引脚连接着蓝牙的开关机引脚,高电平开机,低电平关机,我 ...

  9. angular : $eval & $timeout

    $digest: function() { var watch, value, last, watchers, length, dirty, ttl = TTL, next, current, tar ...

  10. everything 快速搜索有代价

    我在一台电脑上运行过everything后,把它拷贝到另一台电脑上运行,前一台电脑上的搜索结果记录居然还,包括文件类型,标题,大小,位置.天呐··· 虽然看不到内容,但对于一个社工来说,一个标题完全足 ...