2012-03-03 9 views
1

php関数sprintfは正確な値を返しません。php sprintfは正確な値を返しません

のサンプルコードは以下の通りです:

<?php 
$var1 = 10469116213008843; 
echo $var1; 
echo "\n"; 

$var2 = sprintf("%.0f", $var1); 
echo $var2; 
echo "\n"; 
?> 

は、結果がどうなるかを推測しますか? 32ビットOS上の

10469116213008843 
10469116213008844 

を、それが生産:、それが生産する64ビットOS上の

1.0469116213009E+16 
10469116213008844 

私はなぜ、本当に混乱していますか?

#include <stdio.h> 

/** 
* 18456116213465313, 18456116950744489, 17705116944636053, 
* 18456116950744489, 13368116212523055, 10469116213008843, 
* 19986116955764391, 19591116945040018, 11882116944120195, 
* 19166116210920723, 19166116210920723 
*/ 
int main() 
{ 
    double oddVariable = 18456116213465313; 
    printf("%0.f\n", oddVariable); 

    oddVariable = 18456116213465313; 
    printf("%.0f\n", oddVariable); 

    oddVariable = 18456116213465313; 
    printf("%.0f\n", oddVariable); 

    return 0; 

} 
+0

は実用的か理論的な質問ですか? –

+0

10469116213008843は大きすぎて整数値として保持できないため、浮動小数点として保持されます。浮動小数点精度の標準コンピュータ言語警告が適用されます。 –

+0

@ Col.Shrapnel私は私のプロジェクトでこの問題に出会って、週末全体を壊しました。ランタイムログを観察した後、私はsprintf関数に関するすべてであることを理解していました...それは正確な値を返しません... – hellojinjie

答えて

2

一部の数値は整数で保持するには大きすぎるため、浮動小数点数式で近似しています。このマグニチュードのままで作業する必要がある場合は、BC MathまたはGMPのような拡張子を使用することを検討してください。これらの拡張機能により、非常に大きな数の操作を実行し、完全な文字列表現を出力することができます。

+0

...または[GMP](http://php.net/gmp)または[Math_BigInteger](http://phpseclib.sourceforge.net/)を参照してください。 – rodneyrehm

+0

と3つすべてが問題とはまったく関係ありません –

関連する問題