1. ホーム
  2. c++

[解決済み] QueryPerformanceCounterの使い方を教えてください。

2022-12-14 03:42:26

質問

最近、タイマクラスでミリ秒からマイクロ秒に変更する必要があると判断し、いくつかの研究の後、QueryPerformanceCounterがおそらく私の最も安全な賭けであると判断しました。(警告は Boost::Posix にある、Win32 APIで動作しないかもしれないという警告は、私を少し遠ざけた)。しかし、私はそれを実装する方法がよくわかりません。

私がやっていることは、どんな GetTicks() 的な関数を呼び出して、それを Timer の startingTicks 変数に代入しています。そして、経過時間を求めるには、関数の戻り値を startingTicks そしてタイマーをリセットするときは、関数をもう一度呼び出して startTicks を代入するだけです。残念ながら、私が見たコードでは、単に QueryPerformanceCounter() を呼び出すほど単純ではなく、引数として何を渡せばいいのかわかりません。

どのように解決するのですか?

#include <windows.h>

double PCFreq = 0.0;
__int64 CounterStart = 0;

void StartCounter()
{
    LARGE_INTEGER li;
    if(!QueryPerformanceFrequency(&li))
    cout << "QueryPerformanceFrequency failed!\n";

    PCFreq = double(li.QuadPart)/1000.0;

    QueryPerformanceCounter(&li);
    CounterStart = li.QuadPart;
}
double GetCounter()
{
    LARGE_INTEGER li;
    QueryPerformanceCounter(&li);
    return double(li.QuadPart-CounterStart)/PCFreq;
}

int main()
{
    StartCounter();
    Sleep(1000);
    cout << GetCounter() <<"\n";
    return 0;
}

このプログラムは1000に近い数値を出力するはずです(Windowsのスリープはそれほど正確ではありませんが、999のような数値になるはずです)。

このプログラムは StartCounter() 関数は、パフォーマンス・カウンタの刻み数を CounterStart 変数に記録します。このとき GetCounter() から何ミリ秒経ったかを返します。 StartCounter() が最後に呼び出されてからの経過時間を double で返します。 GetCounter() が 0.001 を返すなら、それは StartCounter() が呼び出されてから約1マイクロ秒経過したことになる。

もし、タイマーを秒単位で表示させたい場合は

PCFreq = double(li.QuadPart)/1000.0;

から

PCFreq = double(li.QuadPart);

または、マイクロ秒が必要な場合は

PCFreq = double(li.QuadPart)/1000000.0;

しかし、実際にはdoubleを返すので、利便性のためです。