<?
02 /*
03 * 一个抽奖类,精确到万分之一
04 * 三个步骤:1.接受一个中奖概率数组;2.接受一个抽奖种子;3.返回中奖等级
05 */
06
07 class Lottery {
08 /*
09 * 中奖概率数组,自动判断奖项数目
10 * 数组键值和为100,自动计算出不中奖的概率,若初始是超过100抛出一个错误
11 */
12
13 protected $_rate = array();
14
15 /*
16 * 设置中奖概率,
17 * @param Array,中奖概率,以数组形式传入
18 */
19
20 public function setRate($rate = array(12.1, 34)) {
21 $this->_rate = $rate;
22 if (array_sum($this->_rate) > 100)//检测概率设置是否有问题
23 throw new Exception('Winning rate upto 100%');
24 if (array_sum($this->_rate) < 100)
25 //定义未中奖情况的概率,用户给的概率只和为100时,则忽略0
26 $this->_rate[] = 100 - array_sum($this->_rate);
27 }
28
29 /*
30 * 随机生成一个1-10000的整数种子,提交给中奖判断函数
31 * @return int,按传入的概率排序,返回中奖的项数
32 */
33
34 public function runOnce() {
35 return $this->judge(mt_rand(0, 10000));
36 }
37
38 /*
39 * 按所设置的概率,判断一个传入的随机值是否中奖
40 * @param int,$seed 10000以内的随机数
41 * @return int,$i 按传入的概率排序,返回中奖的项数
42 */
43
44 protected function judge($seed) {
45 foreach ($this->_rate as $key => $value) {
46 $tmpArr[$key + 1] = $value * 100;
47 }
48 //将概率乘十后累计,以便随机选择,组合成
49 $tmpArr[0] = 0;
50 foreach ($tmpArr as $key => $value) {
51 if ($key > 0) {
52 $tmpArr[$key] += $tmpArr[$key - 1];
53 }
54 }
55 for ($i = 1; $i < count($tmpArr); $i++) {
56 if ($tmpArr[$i - 1] < $seed && $seed <= $tmpArr[$i]) {
57 return $i; //返回中奖的项数(按概率的设置顺序)
58 }
59 }
60 }
61
62 }
63
64 $rate = array(33, 20, 2, 0.95, 12, 4.55);
65
66 $a = new Lottery;
67 $a->setRate($rate);
68 for ($i = 0; $i <= 10000; $i++) {
69 $b = $a->runOnce();
70 @$rewards[$b]++;
71 }
72 unset($rewards['']);
73 echo array_sum($rewards);
74 ?>
75 <html>
76 <head>
77 <meta http-equiv="Content-Type" content="text/html; charset=utf8" />
78 </head>
79 <body>
80 <table>
81 <thead>运行10000次,对比设置概率和中奖次数</thead>
82 <tr><th>设置概率</th><th>中奖次数</th></tr>
83 <tr><td><?php echo $rate[0]; ?>%</td><td><?php echo $rewards[1] ?></td></tr>
84 <tr><td><?php echo $rate[1]; ?>%</td><td><?php echo $rewards[2] ?></td></tr>
85 <tr><td><?php echo $rate[2]; ?>%</td><td><?php echo $rewards[3] ?></td></tr>
86 <tr><td><?php echo $rate[3]; ?>%</td><td><?php echo $rewards[4] ?></td></tr>
87 <tr><td><?php echo $rate[4]; ?>%</td><td><?php echo $rewards[5] ?></td></tr>
88 <tr><td><?php echo $rate[5]; ?>%</td><td><?php echo $rewards[6] ?></td></tr>
89 <tr><td><?php echo 'miss'; ?></td><td><?php echo $rewards[7] ?></td></tr>
90 </table>
91 </body>
92 </html>