PHP 可靠计算立方根

标签 php math floating-point-precision

这似乎是理所当然的事情,但我很难解决这个问题:

我想根据给定的经验值(exp)计算等级。因此,我使用立方根公式并向下舍入到下一个整数。当 exp 恰好达到 level^3 时,就达到了下一个级别。级别的数量是无限的,所以我会避免使用预先计算的查找表。

当我使用标准 php 数学时

floor( pow( 10648, 1/3))

它返回 21 而不是 22。这是错误的,因为 21^3 给出 92161。原因是由于浮点精度有限,pow(10648, 1/3) 返回的不完全是 22,而是返回 21.9993112732。 您可以使用以下代码片段进行检查:

$lvl = pow( 10647, (float) 1 / 3);
print number_format( $lvl, 10);

这是我的解决方法。但我不确定这是否是防弹的:

public static function getLevel($exp) {    
    $lvl = floor(pow($exp, (float) 1 / 3));    // calculate the level
    if (pow($lvl + 1, 3) == $exp) {            // make check
        $lvl++;                                // correct 
    }
    return $lvl;
}

而且在检查时它看起来有点脆弱。所以问题依然存在: 是否有一种可靠、高效且防弹的方法来计算(正数)立方根。

谢谢。

最佳答案

我认为这是您的代码需要的唯一修改:

public static function getLevel($exp) {    
    $lvl = floor(pow($exp, (float) 1 / 3));    
    if (pow($lvl + 1, 3) <= $exp) {   // compare with <= instead of ==         
        $lvl++;                                 
    }
    return $lvl;
}

关于PHP 可靠计算立方根,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26647613/

相关文章:

php - Imagick 未在 PHP 中加载

java - 为什么将 float 除以整数返回 0.0?

较少的编译器在 Linux 和 OSX 上使用不同的浮点精度

javascript - JavaScript 中的舍入问题

php - MySQL 查询 - 15 天前 End_date 到 End_date 之间的记录

php - 将 Google Analytics 添加到 PHP 网站

java - 从 xy 移动到另一点,我在时间 t 在哪里?

python - numpy.power() 和 math.pow() 不给出相同的结果

php - 如何在 PHP 中将数字转换为字母?

javascript - 旋转六边形上的索引