QueryPerformanceCounterから返された時間値をミリ秒単位のdouble値に変換するコードがいくつかあります。double型の不正確な除算(Visual C++ 2008)
関数は次のようになります。
double timeGetExactTime() {
LARGE_INTEGER timerPerformanceCounter, timerPerformanceFrequency;
QueryPerformanceCounter(&timerPerformanceCounter);
if (QueryPerformanceFrequency(&timerPerformanceFrequency)) {
return (double)timerPerformanceCounter.QuadPart/(((double)timerPerformanceFrequency.QuadPart)/1000.0);
}
return 0.0;
}
私は(私は前にこの問題を抱えていたとは思わない、と何も変更がコードに行われていない)最近抱えている問題は、その結果でありますあまり正確ではありません。結果には小数点は含まれませんが、1ミリ秒よりも精度は低くなります。
デバッガで式を入力すると、予想通りの結果が得られます。
私は、64ビット整数の精度を保持することはできませんが、現時点でPerformanceCounterは46ビットしか必要としないことを理解しています(ダブルは52ビットを損失なしで格納できるはずです) さらに、デバッガが別の形式を使用して分割を実行することになります。
ここに私が得たいくつかの結果があります。プログラムはデバッグモードでコンパイルされた、C++オプションで浮動小数点モードがデフォルト(精密(/ FP:正確な))に設定した
timerPerformanceCounter.QuadPart: 30270310439445
timerPerformanceFrequency.QuadPart: 14318180
double perfCounter = (double)timerPerformanceCounter.QuadPart;
30270310439445.000
double perfFrequency = (((double)timerPerformanceFrequency.QuadPart)/1000.0);
14318.179687500000
double result = perfCounter/perfFrequency;
2114117248.0000000
return (double)timerPerformanceCounter.QuadPart/(((double)timerPerformanceFrequency.QuadPart)/1000.0);
2114117248.0000000
Result with same expression in debugger:
2114117188.0396111
Result of perfTimerCount/perfTimerFreq in debugger:
2114117234.1810646
Result of 30270310439445/14318180 in calculator:
2114117188.0396111796331656677036
精度がに比べデバッガのウォッチで異なる理由を誰もが知っています私のプログラムの結果は?
更新:変換と除算を実行する前に、timerPerformanceCounter.QuadPartから30270310439445を差し引いてみましたが、すべての場合に正確に表示されます。 私のコンピュータの稼働時間が今16日になっているので、私はこの動作を見ているだけなのかもしれません。 したがって、大きな数値では除算の精度の問題があるように見えますが、ウォッチウィンドウでディビジョンがまだ正しい理由はまだ説明されていません。 結果が倍精度よりも高い精度の型を使用していますか?