8

私は、非常に重い CPU 作業 (すべて数学と計算) を実行する C++ ライブラリを作成しました。独自のデバイスに任せると、利用可能なすべての CPU リソースの 100% を簡単に消費します (利用可能な論理リソースの数までマルチスレッド化されています)。マシン上のコア)。

そのため、ライブラリを使用するソフトウェアが呼び出すことになっているメインの計算ループ内にコールバックがあります。

while(true)
{
    //do math here
    callback(percent_complete);
}

コールバックで、クライアントは Sleep(x) を呼び出してスレッドを遅くします。

元々、クライアント側のコードは固定の Sleep(100) 呼び出しでしたが、一部のマシンは他のマシンよりも速く計算を終了するため、信頼性の低いパフォーマンスが低下しましたが、スリープはすべてのマシンで同じです。したがって、クライアントはシステム時間をチェックし、1 秒以上 (== 数回の反復) が経過した場合、0.5 秒間スリープします。

これは、スレッドを遅くする許容可能な方法ですか? パフォーマンスを最大化するには、Sleep() の代わりにセマフォ/ミューテックスを使用する必要がありますか? 処理の 1 秒ごとに x ミリ秒のスリープは問題ありませんか、それとも私が気づいていない何か問題がありますか?

私が尋ねた理由は、タスクマンがプロセスが CPU の約 10% を占めていることを示しているにもかかわらず、マシンがまだひどく動かなくなっているからです。私はすでにハードディスクとメモリの競合を無駄に調査したので、スレッドを遅くしている方法がこの問題を引き起こしているのではないかと思っています.

ありがとう!

4

5 に答える 5

23

計算スレッドの優先度を下げてみませんか? これにより、他のスレッドを実行する必要がない場合は、計算スレッドをできるだけ速く実行できるようにしながら、他のスレッドが確実にスケジュールされます。

于 2010-01-17T15:28:12.267 に答える
4

CPU が 100% で何が問題になっていますか? それはあなたが努力すべきことであり、避けようとするのではありません。これらの数学の計算は重要ですよね?OS によって明示的に管理されておらず、メイン スレッドによって使用されている他のリソース (ミューテックス、ディスクなど) を占有することを避けようとしている場合を除き、通常、スレッドを遅くしようとするのは悪い考えです。マルチコア システム (ほぼすべてのシステムが今後そうなる) ではどうですか? まったく理由もなく、スレッドを遅くすることになります。

OS には、スレッド クォンタムの概念があります。システム上の重要なスレッドが枯渇しないようにします。また、前述したように、マルチコア システムでは、1 つの CPU で 1 つのスレッドをスパイクしても、他のコアの他のスレッドのパフォーマンスはまったく損なわれません。

また、別のコメントで、このスレッドも多くのディスク I/O を実行していることがわかります。これらの操作により、スレッドが結果を待っている間にスレッドが既に解放されるため、スリープは何もしません。

一般に、Sleep(x) を呼び出している場合は、設計に問題があるか怠惰であり、x==0 の場合は、ライブロックに対して自分自身を開いています (Sleep(0) を呼び出しているスレッドは、実際にはすぐに再スケジュールされ、ヌープになります)。

于 2010-01-17T17:50:48.260 に答える
2

あなたのコメントからあなたが求めているのは、アプリを調整するのに睡眠は問題ないはずです. おそらく、睡眠時間をもっと正確にする必要があるだけです。

このような機能を使用する唯一のソフトウェアは、BOINC クライアントです。どんなメカニズムを使っているのかはわかりませんが、オープンソースでマルチプラットフォームなので、自分で助けてください.

構成オプションがあります (「CPU 使用率を X% に制限する」)。私がそれを実装する方法は、 や などのプラットフォーム依存の API を使用しclock()GetSystemTimes()プロセッサ時間を経過したウォール クロック時間と比較することです。少し実際の作業を行い、標準を上回っているか下回っているかを確認し、標準を上回っている場合は、しばらく寝て標準以下に戻します。

BOINC クライアントは優先度を適切に処理し、最大 CPU が 100% の場合でも他のアプリにパフォーマンスの問題を引き起こしません。私がスロットルを使用する理由は、それ以外の場合、クライアントが常に CPU をフル稼働させ、ファンの速度とノイズを増加させるためです。なので、ファンが静かになるレベルで動かしています。より良い冷却があれば、多分私はそれを必要としないでしょう:-)

于 2010-01-17T15:43:19.843 に答える
0

cpulimitを見てください。プロセスを特定の CPU 使用率以下に保つために、必要に応じてSIGSTOPおよびを送信します。SIGCONT

それでも、「あなたのソフトウェアがPCのパフォーマンスを殺しているというクレイジーな苦情と風変わりなレビュー」のWTF. あなたのソフトウェアが遅く、私のハードウェアを最大限に活用していないと不平を言う可能性が高いですが、私はあなたの顧客ではありません.

編集: Windows 上で、SuspendThread()おそらくResumeThread()同様の動作を生成する可能性があります。

于 2010-01-17T15:53:00.993 に答える
0

それほど複雑ではない別の方法として、1 回の繰り返しの時間を計り、次の繰り返しの前にスレッドを (x * t) ミリ秒間スリープさせることができます。ここで、t は 1 回の繰り返しのミリ秒時間であり、x は選択されたスリープ時間の割合 (0 から1)。

于 2010-01-17T16:14:15.997 に答える