Разные значения пи? - PullRequest
0 голосов
/ 21 мая 2018
ini_set('precision', 64);    
echo M_PI."<br>";
echo pi()."<br>";
echo "3.14159265358979323846264338327950<br>";

Для справки я использовал http://www.eveandersson.com/pi/digits/100

Если вы сравните вывод, вы получите следующее:

3.1415926535898
3.141592653589793115997963468544185161590576171875
3.14159265358979323846264338327950

Так что со значением точности pi()?Кажется, он полностью выключен.Да, я знаю, что пи иррационально, но по крайней мере до 100 значащих цифр оно должно быть точным?

Кто-нибудь может подтвердить эту проблему, и можно ли объяснить, почему после 16 цифр в php происходит ошибка?

Ответы [ 2 ]

0 голосов
/ 21 мая 2018

На странице руководства по расширениям bcmath представлено следующее:

//bcpi function with Gauss-Legendre algorithm
//by Chao Xu (Mgccl)

function bcpi($precision){
  $n=0;
    $limit = ceil(log($precision)/log(2))-1;
    bcscale($precision+6);
    $a = 1;
    $b = bcdiv(1,bcsqrt(2));
    $t = 1/4;
    $p = 1;
    while($n < $limit){
        $x = bcdiv(bcadd($a,$b),2);
        $y = bcsqrt(bcmul($a, $b));
        $t = bcsub($t, bcmul($p,bcpow(bcsub($a,$x),2)));
        $a = $x;
        $b = $y;
        $p = bcmul(2,$p);
        ++$n;
    }
    return bcdiv(bcpow(bcadd($a, $b),2),bcmul(4,$t),$precision);
}

echo bcpi(64);
echo "<br>3.1415926535897932384626433832795028841971693993751058209749445923";

Похоже, что ini_set ('precision', 64);не делает ничего конструктивного для обычных математических функций php (> 15), но расширение bcmath полностью игнорирует настройку.

Поэтому, чтобы работать с точностью> = 16, используйте расширение bcmath, иначе ini_set работает до 15

И ответ @ Progman о том, что правила хранения чисел с плавающей запятой / двойного числа все еще применяются - означает, что есть ограничение на 15 десятичных знаков (даже если php хранит все числа с плавающей запятой как двойные)

0 голосов
/ 21 мая 2018

Проблема заключается в том, что значение M_PI (то же самое значение, которое возвращается pi()) жестко закодировано.

Из файла php_math.h:

#ifndef M_PI
#define M_PI           3.14159265358979323846  /* pi */
#endif

Изменение точности не приводит к изменению уже определенного постоянного значения.Кроме того, по-прежнему применимо обычное «как хранятся числа с плавающей запятой / двойные числа».

...