COCOS 2 DX WIN 32版のCPU占有率25%改良策
2503 ワード
主サイクルでSleep(0)を使用している可能性があると推測し、検索すると、cococos 2 dxplatformwin 32CCApplicationに位置する具体的なコードにナビゲートします.cppは、大きく似ています.
すなわち,このループはmainLoopを実行する以外に,メッセージのチェックやSleep(0)に多くの時間を費やした.
そして、私はまた奇妙な現象を発見しました(なぜかはまだ分かりません).
HelloCPPプロジェクトのAppDelegate.cppファイルにはコードが1行あります.
上の60は、大きくすれば何の役にも立たず、フレームレートは常に60で変わりません.しかし、60未満に変更すれば、役に立ちます.
そこで,CPU占有を解決する考え方は,「サイクル精度を下げることができるかどうか」という考えから始まる.
通常、Sleep(1)を実行すると、約1/50秒眠ることが知られており、この時間は正確ではなく、正確ではなく、60 fpsというスムーズなニーズを満たすことができないように見えます.しかし、ゲームがフレームレートをこんなに高くする必要がない場合は、例えば30 fps??この案は大いに実行可能である.
実際のテストにより,Sleep(0)をSleep(1)に変更し,上のコードの60を25に変更すると,非常に顕著な効果が得られた.しかし、もう一つの問題は、ゲームのサイクルごとにやることが少し多く、時間が少し長いと、ゲームが遅くなります.
元のengineでは、同期時間のコードは次のとおりです.
nLastにnNow時間を記録し、時間差と設定間隔を比較するたびに、設定間隔よりも時間差が大きくなることが多いため、不正確なSleep(1)やサイクル毎の負担が大きい場合には、フレーム毎に実際にかかる時間が設定間隔を超えて多くなり、ゲーム速度が遅くなる(ゲームがフレームステップで計時される場合).
この問題を解決するために、私は時間の位置合わせを使っています.実はnLastを更新する式を変更しました.
これにより、フレーム当たりの総消費時間はかなり一定になります.
上の問題の解決はあまり完璧ではない.どのように60 fpsを維持してもcpu 0%を占有することができますか?私が考えている案はSleep(1)の精度を修正することです.
資料を探してみるとWinmm.libライブラリにはtimeBeginPeriod(1)があります. timeEndPeriod(1);関数はこの目的で使用でき、Sleep(1)の精度を1ミリ秒レベルに向上させ、変更します.
1.Winmmを追加する.libライブラリの参照.私はここでCCApplicationを採用しました.cppヘッダにpragma comment(lib,“Winmm.lib”)文を追加する方法.
2.while(1)コードセグメントの前後に、timeBeginPeriod(1)をそれぞれ載せる. timeEndPeriod(1);ステートメント
これで完成します.
試験により、フレームレートは59 fps以内に設定され、cpuはいずれも0占有(i 7 2600 k)を実現できる.60にすると、cpuが周期的な変なフローティングを占有し、しばらくは不明です.60+にすると、cpuは100%になります.
しかし、この問題は一時的に一段落しても、まずプログラムを50 fpsに限定すればよく、スムーズで、問題なく、感覚的に計算しやすい...
1
while
( 1 ) {
2
if
( ) {
3
if
( ) , call ;
4
else
Sleep(0);
5
}
6
//
7
}
すなわち,このループはmainLoopを実行する以外に,メッセージのチェックやSleep(0)に多くの時間を費やした.
そして、私はまた奇妙な現象を発見しました(なぜかはまだ分かりません).
HelloCPPプロジェクトのAppDelegate.cppファイルにはコードが1行あります.
// set FPS. the default value is 1.0/60 if you don't call this
pDirector->setAnimationInterval(1.0 / 60);
上の60は、大きくすれば何の役にも立たず、フレームレートは常に60で変わりません.しかし、60未満に変更すれば、役に立ちます.
そこで,CPU占有を解決する考え方は,「サイクル精度を下げることができるかどうか」という考えから始まる.
通常、Sleep(1)を実行すると、約1/50秒眠ることが知られており、この時間は正確ではなく、正確ではなく、60 fpsというスムーズなニーズを満たすことができないように見えます.しかし、ゲームがフレームレートをこんなに高くする必要がない場合は、例えば30 fps??この案は大いに実行可能である.
実際のテストにより,Sleep(0)をSleep(1)に変更し,上のコードの60を25に変更すると,非常に顕著な効果が得られた.しかし、もう一つの問題は、ゲームのサイクルごとにやることが少し多く、時間が少し長いと、ゲームが遅くなります.
元のengineでは、同期時間のコードは次のとおりです.
QueryPerformanceCounter(&nNow);
if
(nNow.QuadPart - nLast.QuadPart > m_nAnimationInterval.QuadPart) {
nLast.QuadPart = nNow.QuadPart;
nLastにnNow時間を記録し、時間差と設定間隔を比較するたびに、設定間隔よりも時間差が大きくなることが多いため、不正確なSleep(1)やサイクル毎の負担が大きい場合には、フレーム毎に実際にかかる時間が設定間隔を超えて多くなり、ゲーム速度が遅くなる(ゲームがフレームステップで計時される場合).
この問題を解決するために、私は時間の位置合わせを使っています.実はnLastを更新する式を変更しました.
nLast.QuadPart = nNow.QuadPart - (nNow.QuadPart %m_nAnimationInterval.QuadPart);
これにより、フレーム当たりの総消費時間はかなり一定になります.
上の問題の解決はあまり完璧ではない.どのように60 fpsを維持してもcpu 0%を占有することができますか?私が考えている案はSleep(1)の精度を修正することです.
資料を探してみるとWinmm.libライブラリにはtimeBeginPeriod(1)があります. timeEndPeriod(1);関数はこの目的で使用でき、Sleep(1)の精度を1ミリ秒レベルに向上させ、変更します.
1.Winmmを追加する.libライブラリの参照.私はここでCCApplicationを採用しました.cppヘッダにpragma comment(lib,“Winmm.lib”)文を追加する方法.
2.while(1)コードセグメントの前後に、timeBeginPeriod(1)をそれぞれ載せる. timeEndPeriod(1);ステートメント
これで完成します.
試験により、フレームレートは59 fps以内に設定され、cpuはいずれも0占有(i 7 2600 k)を実現できる.60にすると、cpuが周期的な変なフローティングを占有し、しばらくは不明です.60+にすると、cpuは100%になります.
しかし、この問題は一時的に一段落しても、まずプログラムを50 fpsに限定すればよく、スムーズで、問題なく、感覚的に計算しやすい...