php 抽奖 可控概率



```/**
    * 计算可控概率
    * 根据传入的数组及其权重,随机返回一个元素,其返回概率由元素的权重决定。
    * @param array $arr 包含元素及其权重的数组,每个元素应是一个数组,其中包含'weight'键用于指定权重。
    * @param string $weight_key 数组元素中用于指定权重的键名,默认为'weight'。
    * @return mixed 返回数组中随机选择的元素。
    */
   public function controllableProbability($arr, $weight_key = 'weight') {
       // 初始化总概率
       $total_probability = 0;
       // 遍历数组,计算所有元素权重的总和
       foreach($arr as $v) {
           // 使用bcadd函数处理浮点数加法,确保精度
           $total_probability = bcadd((string)$total_probability, (string)$v[$weight_key], 2);
       }
       // 生成一个介于1和总概率之间的随机数
       $rand = mt_rand(1, intval($total_probability));
       // 重新遍历数组,根据随机数和元素权重确定返回哪个元素
       foreach ($arr as $val) {
           // 如果随机数小于等于当前元素的权重,则选择当前元素
           if ($rand <= $val[$weight_key]) {break;}
           // 从随机数中减去当前元素的权重,继续检查下一个元素
           $rand -= $val[$weight_key];
           // 移动到数组的下一个元素
           next($arr);
       }
       // 返回选中的元素
       //想要返回key,使用return key($arr);
       return current($arr);
   }

  public function test1()
    {
        $arr = [
            ['id' => 1, 'name' => '谢谢惠顾', 'weight' => 10],
            ['id' => 2, 'name' => '中10元', 'weight' => 5],
            ['id' => 3, 'name' => '中2元', 'weight' => 1],
            ['id' => 4, 'name' => '中50W', 'weight' => 0],
        ];

        $result = $this->controllableProbability($arr);
        return $result['name'];
        // 测试
        $a = 0; $b = 0; $c = 0; $d = 0;
        for($i = 0; $i < 160000; $i++) {
            $res =  $this->controllableProbability($arr, 'weight');
            if($res['id'] == 1) $a ++;
            if($res['id'] == 2) $b ++;
            if($res['id'] == 3) $c ++;
            if($res['id'] == 4) $d ++;
        }
        echo "$a $b $c $d";

    }

  • 8
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
转盘抽奖是一种常见的互动活动,可以通过HTML和JavaScript来实现可控的转盘抽奖效果。以下是一种简单的实现方式: 1. 首先,在HTML中创建一个转盘的容器,可以使用`<div>`元素,并设置其样式和大小。 2. 在容器中创建一个圆形的转盘,可以使用`<canvas>`元素,并设置其大小和位置。 3. 使用JavaScript编写转盘的逻辑代码。首先,需要定义转盘的奖品和对应的角度范围。然后,根据用户的操作(如点击按钮),计算出随机的中奖角度,并将转盘旋转到该角度。 4. 在转盘上绘制奖品和指针。可以使用`<canvas>`元素的API来实现绘制功能,如`arc()`方法绘制圆弧、`fillText()`方法绘制文字等。 5. 添加交互功能,如点击按钮开始抽奖、显示中奖结果等。 下面是一个简单的示例代码: ```html <!DOCTYPE html> <html> <head> <title>转盘抽奖</title> <style> #container { width: 400px; height: 400px; position: relative; } #canvas { position: absolute; top: 0; left: 0; } #btn { position: absolute; bottom: 20px; left: 50%; transform: translateX(-50%); padding: 10px 20px; background-color: #f00; color: #fff; cursor: pointer; } </style> </head> <body> <div id="container"> <canvas id="canvas" width="400" height="400"></canvas> <button id="btn">开始抽奖</button> </div> <script> var canvas = document.getElementById('canvas'); var ctx = canvas.getContext('2d'); var btn = document.getElementById('btn'); // 奖品和对应的角度范围 var prizes = [ { name: '奖品1', startAngle: 0, endAngle: 60 }, { name: '奖品2', startAngle: 60, endAngle: 120 }, { name: '奖品3', startAngle: 120, endAngle: 180 }, // 其他奖品... ]; // 绘制转盘 function drawWheel() { ctx.clearRect(0, 0, canvas.width, canvas.height); ctx.lineWidth = 2; ctx.strokeStyle = '#000'; var centerX = canvas.width / 2; var centerY = canvas.height / 2; var radius = Math.min(canvas.width, canvas.height) / 2 - 10; ctx.beginPath(); ctx.arc(centerX, centerY, radius, 0, Math.PI * 2); ctx.stroke(); // 绘制奖品 ctx.font = '16px Arial'; ctx.textAlign = 'center'; ctx.textBaseline = 'middle'; for (var i = 0; i < prizes.length; i++) { var prize = prizes[i]; var angle = (prize.startAngle + prize.endAngle) / 2; var x = centerX + Math.cos(angle * Math.PI / 180) * radius * 0.8; var y = centerY Math.sin(angle * Math.PI / 180) * radius * 0.8; ctx.fillText(prize.name, x, y); } // 绘制指针 ctx.beginPath(); ctx.moveTo(centerX, centerY - radius); ctx.lineTo(centerX - 10, centerY - radius - ); ctx.lineTo(centerX + 10, centerY - radius - 20); ctx.closePath(); ctx.fillStyle = '#f00'; ctx.fill(); } // 开始抽奖 function startLottery() { var randomAngle = Math.random() * 360; // 随机生成中奖角度 var rotateAngle = randomAngle + 360 * 5; // 转盘旋转的总角度 canvas.style.transformOrigin = 'center center'; canvas.style.transition = 'transform 5s'; canvas.style.transform = 'rotate(' + rotateAngle + 'deg)'; setTimeout(function() { var prize = getPrize(randomAngle); alert('恭喜您获得了' + prize.name); }, 5000); } // 根据角度获取对应的奖品 function getPrize(angle) { for (var i = 0; i < prizes.length; i++) { var prize = prizes[i]; if (angle >= prize.startAngle && angle < prize.endAngle) { return prize; } } } drawWheel(); btn.addEventListener('click', startLottery); </script> </body> </html> ``` 这段代码实现了一个简单的转盘抽奖效果,用户点击按钮后,转盘会旋转一段时间后停止,并弹出中奖结果。你可以根据自己的需求进行修改和扩展。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值