java编写抽奖程序 抽奖程序源代码



文章插图
java编写抽奖程序 抽奖程序源代码

文章插图
概述
项目开发中经常会有抽奖这样的营销活动的需求,例如:积分大转盘、刮刮乐、老虎机等等多种形式,其实后台的实现方法是一样的,本文介绍一种常用的抽奖实现方法 。
整个抽奖过程包括以下几个方面:
奖品奖品池抽奖算法奖品限制奖品发放奖品奖品包括奖品、奖品概率和限制、奖品记录 。
【java编写抽奖程序 抽奖程序源代码】奖品表:
CREATE TABLE `points_luck_draw_prize` (`id` bigint(20) NOT NULL AUTO_INCREMENT,`name` varchar(50) DEFAULT NULL COMMENT '奖品名称',`url` varchar(50) DEFAULT NULL COMMENT '图片地址',`value` varchar(20) DEFAULT NULL,`type` tinyint(4) DEFAULT NULL COMMENT '类型1:红包2:积分3:体验金4:谢谢惠顾5:自定义',`status` tinyint(4) DEFAULT NULL COMMENT '状态',`is_del` bit(1) DEFAULT NULL COMMENT '是否删除',`position` int(5) DEFAULT NULL COMMENT '位置',`phase` int(10) DEFAULT NULL COMMENT '期数',`create_time` datetime DEFAULT NULL,`update_time` datetime DEFAULT NULL,PRIMARY KEY (`id`)) ENGINE=InnoDB AUTO_INCREMENT=164 DEFAULT CHARSET=utf8mb4 COMMENT='奖品表';奖品概率限制表:
CREATE TABLE `points_luck_draw_probability` (`id` bigint(20) NOT NULL AUTO_INCREMENT,`points_prize_id` bigint(20) DEFAULT NULL COMMENT '奖品ID',`points_prize_phase` int(10) DEFAULT NULL COMMENT '奖品期数',`probability` float(4,2) DEFAULT NULL COMMENT '概率',`frozen` int(11) DEFAULT NULL COMMENT '商品抽中后的冷冻次数',`prize_day_max_times` int(11) DEFAULT NULL COMMENT '该商品平台每天最多抽中的次数',`user_prize_month_max_times` int(11) DEFAULT NULL COMMENT '每位用户每月最多抽中该商品的次数',`create_time` datetime DEFAULT NULL,`update_time` datetime DEFAULT NULL,PRIMARY KEY (`id`)) ENGINE=InnoDB AUTO_INCREMENT=114 DEFAULT CHARSET=utf8mb4 COMMENT='抽奖概率限制表';奖品记录表:
CREATE TABLE `points_luck_draw_record` (`id` bigint(20) NOT NULL AUTO_INCREMENT,`member_id` bigint(20) DEFAULT NULL COMMENT '用户ID',`member_mobile` varchar(11) DEFAULT NULL COMMENT '中奖用户手机号',`points` int(11) DEFAULT NULL COMMENT '消耗积分',`prize_id` bigint(20) DEFAULT NULL COMMENT '奖品ID',`result` smallint(4) DEFAULT NULL COMMENT '1:中奖 2:未中奖',`month` varchar(10) DEFAULT NULL COMMENT '中奖月份',`daily` date DEFAULT NULL COMMENT '中奖日期(不包括时间)',`create_time` datetime DEFAULT NULL,`update_time` datetime DEFAULT NULL,PRIMARY KEY (`id`)) ENGINE=InnoDB AUTO_INCREMENT=3078 DEFAULT CHARSET=utf8mb4 COMMENT='抽奖记录表';奖品池
奖品池是根据奖品的概率和限制组装成的抽奖用的池子 。主要包括奖品的总池值和每个奖品所占的池值(分为开始值和结束值)两个维度 。最新面试题整理好了,点击Java面试库小程序在线刷题 。
奖品的总池值:所有奖品池值的总和 。每个奖品的池值:算法可以变通,常用的有以下两种方式 :奖品的概率*10000(保证是整数)奖品的概率10000奖品的剩余数量
奖品池bean:
public class PrizePool implements Serializable{/*** 总池值*/private int total;/*** 池中的奖品*/private List<PrizePoolBean> poolBeanList;}池中的奖品bean:
public class PrizePoolBean implements Serializable{/*** 数据库中真实奖品的ID*/private Long id;/*** 奖品的开始池值*/private int begin;/*** 奖品的结束池值*/private int end;}奖品池的组装代码:
/*** 获取超级大富翁的奖品池* @param zillionaireProductMap 超级大富翁奖品map* @param flag true:有现金false:无现金* @return*/private PrizePool getZillionairePrizePool(Map<Long, ActivityProduct> zillionaireProductMap, boolean flag) {//总的奖品池值int total = 0;List<PrizePoolBean> poolBeanList = new ArrayList<>();for(Entry<Long, ActivityProduct> entry : zillionaireProductMap.entrySet()){ActivityProduct product = entry.getValue();//无现金奖品池,过滤掉类型为现金的奖品if(!flag && product.getCategoryId() == ActivityPrizeTypeEnums.XJ.getType()){continue;}//组装奖品池奖品PrizePoolBean prizePoolBean = new PrizePoolBean();prizePoolBean.setId(product.getProductDescriptionId());prizePoolBean.setBengin(total);total = total + product.getEarnings().multiply(new BigDecimal("10000")).intValue();prizePoolBean.setEnd(total);poolBeanList.add(prizePoolBean);}PrizePool prizePool = new PrizePool();prizePool.setTotal(total);prizePool.setPoolBeanList(poolBeanList);return prizePool;}抽奖算法
整个抽奖算法为:
随机奖品池总池值以内的整数循环比较奖品池中的所有奖品,随机数落到哪个奖品的池区间即为哪个奖品中奖 。
推荐一个 Spring Boot 基础教程及实战示例:
https://github.com/javastacks/spring-boot-best-practice