随机舍入
random rounding
所以,我有两个号码,比方说,A 和 B。
A 是任何正数,B 是 0 到 100 之间的百分比。
我需要的是 A 的百分比 B,但随机向上或向下舍入,例如
A = 15, B = 50, result=7(50%) or 8(50%)
A = 10, B = 33, result=3(67%) or 4(33%)
我当前的代码是
floor($A* ($B + rand(0, 9) ) / 100)
但我认为这是不正确的,并且有更好的解决方案。
编辑:
我查看了答案,并实际测试了它们(here)。提交的解决方案的问题在于它们都使用 rand(0,1) 这意味着在 50% 的情况下它总是会精确地向上或向下舍入。但这里有一个问题:例如,让我们再次使用 "A = 10, B = 33" 案例。 B=31 或 B=39 基本上没有区别。我想要的是对应于百分比(例如 31 在 90% 的情况下会产生 3,在 10% 的情况下会产生 4)
从我在回答中看到的情况来看,我原来的解决方案似乎可以正常工作。我本来应该提到它不仅仅是 "random rounding" 并更好地解释第二种情况。
最初的想法是我有一个数组,比方说,10 个项目,我需要得到其中的 33%。我不能一直给出其中的 3 或 4 个,因为它会弄乱整个百分比。所以我需要它至少在长 运行.
统计上是正确的
但无论如何,感谢您的宝贵时间。
与其随机决定四舍五入的方式(这会随机扭曲你的结果,并给你非确定性函数),为什么不做银行家所做的事情 "round to even"?
echo(round(1.5,0,PHP_ROUND_HALF_EVEN) . "<br>");
echo(round(-1.5,0,PHP_ROUND_HALF_EVEN) . "<br>");
这样 4.5 舍入为 4,3.5 舍入为 4。所以 50% 的时间你的中点会向上舍入,50% 的时间你的中点会向下舍入,如你所愿。
为什么不分离计算百分比和决定如何舍入的问题?
$X = $A * $B / 100;
$Y = (rand(0,1) > 0) ? floor($X) : ceil($X);
function myround($a, $b) {
$d = $a * $b / 100.0;
$f = floor($d);
if ((rand() / getrandmax()) > ($d - $f)) return $f + 1.0;
return $f;
}
所以,我有两个号码,比方说,A 和 B。
A 是任何正数,B 是 0 到 100 之间的百分比。
我需要的是 A 的百分比 B,但随机向上或向下舍入,例如
A = 15, B = 50, result=7(50%) or 8(50%)
A = 10, B = 33, result=3(67%) or 4(33%)
我当前的代码是
floor($A* ($B + rand(0, 9) ) / 100)
但我认为这是不正确的,并且有更好的解决方案。
编辑:
我查看了答案,并实际测试了它们(here)。提交的解决方案的问题在于它们都使用 rand(0,1) 这意味着在 50% 的情况下它总是会精确地向上或向下舍入。但这里有一个问题:例如,让我们再次使用 "A = 10, B = 33" 案例。 B=31 或 B=39 基本上没有区别。我想要的是对应于百分比(例如 31 在 90% 的情况下会产生 3,在 10% 的情况下会产生 4)
从我在回答中看到的情况来看,我原来的解决方案似乎可以正常工作。我本来应该提到它不仅仅是 "random rounding" 并更好地解释第二种情况。
最初的想法是我有一个数组,比方说,10 个项目,我需要得到其中的 33%。我不能一直给出其中的 3 或 4 个,因为它会弄乱整个百分比。所以我需要它至少在长 运行.
统计上是正确的但无论如何,感谢您的宝贵时间。
与其随机决定四舍五入的方式(这会随机扭曲你的结果,并给你非确定性函数),为什么不做银行家所做的事情 "round to even"?
echo(round(1.5,0,PHP_ROUND_HALF_EVEN) . "<br>");
echo(round(-1.5,0,PHP_ROUND_HALF_EVEN) . "<br>");
这样 4.5 舍入为 4,3.5 舍入为 4。所以 50% 的时间你的中点会向上舍入,50% 的时间你的中点会向下舍入,如你所愿。
为什么不分离计算百分比和决定如何舍入的问题?
$X = $A * $B / 100;
$Y = (rand(0,1) > 0) ? floor($X) : ceil($X);
function myround($a, $b) {
$d = $a * $b / 100.0;
$f = floor($d);
if ((rand() / getrandmax()) > ($d - $f)) return $f + 1.0;
return $f;
}