I have phantom bug in my code. It appears in one case from 10 attempts. When I try to debug it I found this strange behavior:
$a = floor(1385968017.8665 * 10000); // or (int) (1385968017.8665 * 10000)
// here $a equals to 13859680178664
$b = (1385968017.8665 * 10000);
// here $b equals to 13859680178665
I have such PHP version/configuration:
PHP 5.3.10-1ubuntu3.8 with Suhosin-Patch (cli) (built: Sep 4 2013 20:00:51)
Copyright (c) 1997-2012 The PHP Group
Zend Engine v2.3.0, Copyright (c) 1998-2012 Zend Technologies
with Xdebug v2.2.3, Copyright (c) 2002-2013, by Derick Rethans
UPDATE: I know about floating operations precesion. Same code in C++:
#include <iostream>
int main()
{
std::cout << std::fixed << (1385968017.8665 * 10000) << std::endl;
std::cout << (unsigned long long) (1385968017.8665 * 10000) << std::endl;
return 0;
}
gives me next output:
13859680178664.998047
13859680178664
And it was I expected from it. But why my PHP code shows that (1385968017.8665 * 10000) is precise equals to 13859680178665?
UPDATE 2: As user @core1024 mentioned in comments, PHP possible is rounding result of calculation (1385968017.8665 * 10000). If try php -r 'printf("%f ",1385968017.8665 * 10000);'
result will be somewhere about 13859680178664.998047
. Who can explain when and why PHP do this?
I found explanation for this problem. My php.ini precision setting is equal to 14. If I increase precision setting by one, this stragne behavior not represented:
$a = floor(1385968017.8665 * 10000); // or (int) (1385968017.8665 * 10000)
// here $a equals to 1385968017866(!)5
It runs as expected.
You used the FLOOR()
function in the first statement, which ROUNDS DOWN a value to the nearest integer.
Check here for more info on that.
As to why it rounds down like that, it's because your value 1385968017.8665
isn't exactly that. Jon Skeet explains that here ..along with Tony the Pony.
That's because of 1385968017.8665 is an infinite double in binary, and (literal 1385968017.8665) ~= (1385968017.8664998 in computer).
Is round(1385968017.8665 * 10000) what you need?