Java手动实现一个双色球游戏,每天自己买个彩票玩

前言

之前购买彩票时很少中奖,实际上彩票的中奖概率非常低。在多次尝试后,只中过一次。考虑到中奖机会有限,我决定尝试实现一个彩票自动购买程序,类似于机选功能。这样,我可以更加灵活地进行尝试,而不受实际彩票中奖概率的限制。

代码实现

package demo.game;

import cn.hutool.core.util.RandomUtil;
import com.alibaba.fastjson.JSON;

import java.util.*;

/**
 * @author jisl on 2023/7/31 15:52
 * 双色球彩票
 */

public class DoubleColorBallLottery {

    //    彩票期数
    private int lotteryNumber = 0;

    //    开奖号码
    private Set<Integer> winRedNum = new HashSet<>();
    private int winBlueNum;

    //    用户购买的彩票
    private final List<List<Integer>> userLottery = new ArrayList<>();

    //    用户中奖的彩票
    private final Map<Integer, List<String>> userPrizeLottery = new HashMap<>();

    public int[] lotteryAmount = new int[]{0, 5000000, 1250000, 3000, 200, 10, 5};

  private  static   final int MAX_PRIZE_LEVEL = 6;

    Random random = new Random();

    /**
     * 彩票开奖
     *
     * @author jisl on 2023/7/31 16:06
     **/
    public void lotteryDrawing() {
        winRedNum = buildRedNum();
        winBlueNum = buildBlueNum();
        System.out.printf("[第%s期双色球]开奖结果:红球:%s,蓝球:%s%n", lotteryNumber, JSON.toJSONString(winRedNum), winBlueNum);
    }

    private int buildBlueNum() {
        return random.nextInt(16) + 1;
    }

    private HashSet<Integer> buildRedNum() {
        final HashSet<Integer> set = new HashSet<>();
        while (set.size() < 6) {
            final int randomNum = random.nextInt(33) + 1;
            set.add(randomNum);
        }
        return set;
    }

    /**
     * 买彩票
     *
     * @author jisl on 2023/7/31 16:07
     **/
    public void buy(int count) {
        lotteryNumber = RandomUtil.randomInt(999);
        for (int i = 0; i < count; i++) {
            final ArrayList<Integer> lottery = new ArrayList<>(buildRedNum());
            lottery.add(buildBlueNum());
            userLottery.add(lottery);
        }
    }

    public void redemption() {
//        一到六等奖
        for (int i = 1; i <= MAX_PRIZE_LEVEL; i++) {
            userPrizeLottery.put(i, new ArrayList<>());
        }
        for (List<Integer> lottery : userLottery) {
            int readBallMatches = countMatchingNumbers(lottery);
            boolean blueBallMatch = lottery.get(6) == winBlueNum;
            int prizeItem = calculatePrize(readBallMatches, blueBallMatch);
            if (prizeItem != 0) {
//                中奖了
                final List<String> numbers = userPrizeLottery.get(prizeItem);
                numbers.add(JSON.toJSONString(lottery));
            }
        }
        System.out.println(String.format("[第%s期双色球]中奖结果:", lotteryNumber));
        int userPrizeCount = 0;
        int userPrizeAmount = 0;
        for (int i = 1; i <= MAX_PRIZE_LEVEL; i++) {
            final int userPrizeItemCount = userPrizeLottery.get(i).size();
            userPrizeCount += userPrizeItemCount;
            userPrizeAmount += lotteryAmount[i] * userPrizeItemCount;
            if (i <= 3) {
                System.out.println(String.format("%s等奖中奖个数:%s,中奖号码:%s", i, userPrizeItemCount, userPrizeLottery.get(i)));
            } else {
                System.out.println(String.format("%s等奖中奖个数:%s,中奖号码:-", i, userPrizeItemCount));
            }
        }
//        共计中奖率:6.71%
        System.out.println(String.format("一共买了[%s张]彩票,中奖个数=%s,中奖概率=%s;购买彩票费用=%s,奖金=%s,盈利=%s"
                , userLottery.size(), userPrizeCount, 1.0 * userPrizeCount / userLottery.size(), userLottery.size() * 2, userPrizeAmount, userPrizeAmount - userLottery.size() * 2));
    }


    private int calculatePrize(int readBallMatches, boolean blueBallMatch) {
        if (readBallMatches == 6 && blueBallMatch) {
            return 1;
        } else if (readBallMatches == 6) {
            return 2;
        } else if (readBallMatches == 5 && blueBallMatch) {
            return 3;
        } else if (readBallMatches == 5 || (readBallMatches == 4 && blueBallMatch)) {
            return 4;
        } else if (readBallMatches == 4 || (readBallMatches == 3 && blueBallMatch)) {
            return 5;
        } else if (blueBallMatch) {
            return 6;
        }
        return 0;
    }

    private int countMatchingNumbers(List<Integer> lottery) {
        int count = 0;
        for (int i = 0; i < 6; i++) {
            if (winRedNum.contains(lottery.get(i))) {
                count += 1;
            }
        }
        return count;
    }

    public void game(int n) {
        buy(n);
        lotteryDrawing();
        redemption();
    }

    public static void main(String[] args) {
        final DoubleColorBallLottery lottery = new DoubleColorBallLottery();
        lottery.game(100000);
    }


}

执行效果

[88期双色球]开奖结果:红球:[2,3,19,23,13,29],蓝球:15
[88期双色球]中奖结果:
1等奖中奖个数:0,中奖号码:[]
2等奖中奖个数:0,中奖号码:[]
3等奖中奖个数:0,中奖号码:[]
4等奖中奖个数:43,中奖号码:-
5等奖中奖个数:752,中奖号码:-
6等奖中奖个数:5957,中奖号码:-
一共买了[100000]彩票,中奖个数=6752,中奖概率=0.06752;购买彩票费用=200000,奖金=45905,盈利=-154095

概率计算

一等奖(6+1)中奖概率为:

红球33选6乘以蓝球16选1= C ( 33 , 6 ) × 16 C(33,6)\times16 C(33,6)×16= 33 ! 6 ! × ( 33 − 6 ) ! × 16 \frac{ 33!} {6!\times(33-6)!}\times16 6!×(336)!33!×16= 1 17721088 \frac{1} {17721088} 177210881

二等奖(6+0)中奖概率为:

红球33选6乘以蓝球16选15(红色都中了,蓝色没中是 15 16 \frac{15} {16} 1615)= 15 17721088 \frac {15} {17721088} 1772108815

三等奖(5+1)中奖概率为:

红球33选5乘以蓝球16选1(红色剩下27个数字可以选没中,任意一个球)= 27 × 6 17721088 \frac {27\times6} {17721088} 1772108827×6= 162 17721088 \frac{162}{17721088} 17721088162

四等奖(5+0、4+1)中奖概率为:

红球33选5乘以蓝球16选15+红球33选4乘以蓝球16选1= 27 × 6 × 15 + 6 × 5 ÷ 2 × 27 × 26 ÷ 2 27\times6\times15+6\times5\div2\times27\times26\div2 27×6×15+6×5÷2×27×26÷2= 7695 17721088 \frac{7695} {17721088} 177210887695 (4+1,从27个数可以随机选出两个数,选出的两个数和顺序无关)

五等奖(4+0、3+1)中奖概率为:

红球33选4乘以蓝球16选15+红球33选3乘以蓝球16选1= 27 × 26 ÷ 2 × 6 × 5 ÷ 2 × 15 + 6 × 5 × 4 ÷ 6 × 27 × 26 × 25 ÷ 6 27\times26\div2\times6\times5\div2\times15+6\times5\times4\div6\times27\times26\times25\div6 27×26÷2×6×5÷2×15+6×5×4÷6×27×26×25÷6= 137475 17721088 \frac{137475}{17721088} 17721088137475

六等奖(2+1、1+1、0+1)中奖概率为:

红球33选0乘以蓝球16选1= 6 × 5 × 4 × 3 ÷ ( 4 × 3 × 2 ) × 27 × 26 × 25 × 24 ÷ ( 4 × 3 × 2 ) + 6 × 5 × 4 × 3 × 2 ÷ ( 5 × 4 × 3 × 2 ) × 27 × 26 × 25 × 24 × 23 ÷ ( 5 × 4 × 3 × 2 ) + 6 × 5 × 4 × 3 × 2 × 1 / ( 6 × 5 × 4 × 3 × 2 ) × 27 × 26 × 2 × 24 × 23 × 22 ÷ ( 6 × 5 × 4 × 3 × 2 ) 6\times5\times4\times3\div(4\times3\times2)\times27\times26\times25\times24\div(4\times3\times2)+6\times5\times4\times3\times2\div(5\times4\times3\times2)\times27\times26\times25\times24\times23\div(5\times4\times3\times2)+6\times5\times4\times3\times2\times1/(6\times5\times4\times3\times2)\times27\times26\times2\times24\times23\times22\div(6\times5\times4\times3\times2) 6×5×4×3÷(4×3×2)×27×26×25×24÷(4×3×2)+6×5×4×3×2÷(5×4×3×2)×27×26×25×24×23÷(5×4×3×2)+6×5×4×3×2×1/(6×5×4×3×2)×27×26×2×24×23×22÷(6×5×4×3×2)= 1043640 17721088 \frac{1043640}{17721088} 177210881043640
买了所有的彩票17721088组合,花费17721088*2=35442176=3500万,一共中奖金额= 1043640 × 5 + 137475 × 10 + 7695 × 200 + 162 × 3000 + 15 × 5 × 1 0 6 + 5 × 1 0 6 1043640\times5+137475\times10+7695\times200+162\times3000+15\times5\times10^6+5\times10^6 1043640×5+137475×10+7695×200+162×3000+15×5×106+5×106=88617950。共计中奖率:6.71%

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值