スレッドプールをどのように実装しますか?ウィキペディアで「スレッドプール」を読んでいますが、この質問を解決するために何をすべきかがわかりません(おそらく、スレッドプールが簡単に何であるかを完全に理解していなかったためです)。
誰かがスレッドプールとは何かを平易な英語で説明できますか?
回答
スレッドpoolは、事前にインスタンス化されたアイドルスレッドのグループであり、作業を開始する準備ができています。これらは、実行する短いタスクの数が少ない場合ではなく、タスクごとに新しいスレッドをインスタンス化するよりも優先されます。これにより、スレッドを何度も作成するオーバーヘッドが発生する必要がなくなります。
実装は環境によって異なりますが、簡単に言うと、次のものが必要です。
- スレッドを作成してアイドル状態に保つ方法。これは、プールがスレッドを処理するまで各スレッドをバリアで待機させることで実現できます(これはミューテックスで実行できます)。同様に。)
- キューや、プールにスレッドを追加して引き出す方法を持つその他の構造など、作成されたスレッドを格納するコンテナ。
- 作業を行う際に使用するスレッドの標準インターフェースまたは抽象クラス。これは、
Task
と呼ばれる抽象クラスである可能性があります。execute()
メソッドは、作業を実行してから戻ります。
スレッドプールが作成されると、実装のニーズに応じて、特定の数のスレッドをインスタンス化して使用可能にするか、必要に応じて新しいスレッドを作成します。
プールが渡されたときTask
、コンテナからスレッドを取得し(または、コンテナが空の場合はスレッドが使用可能になるのを待ちます)、Task
を渡します。そして障壁を満たしています。これにより、アイドル状態のスレッドが実行を再開し、指定されたTask
のexecute()
メソッドが呼び出されます。実行が完了すると、スレッドはプールに戻されて再利用のためにコンテナに入れられ、バリアに到達して、サイクルが繰り返されるまでスリープ状態になります。
コメント
- スレッドプールは、事前にインスタンス化されたアイドル状態のスレッドのグループであり、作業を開始する準備ができています。 […]これにより、スレッドを何度も作成するオーバーヘッドが発生するのを防ぐことができます。-誰かが"スレッドを検索するたびに、Googleがこれを吐き出す必要があります。 pool "
- スレッドプールの作成には内部バリアが含まれますか?これらの行で参照を共有できますか?
- @overexchangeいいえ、そうではありません。この質問への私の言及は、バリア質問を書き直すためのより良い方法の例としてでした。 (もしそうなら、私が答えを書きます。)
- 最も短い答えの1つ。
答え
スレッドプールは、通常はキューに編成された管理対象スレッドのコレクションであり、タスクキュー内のタスクを実行します。
非同期で実行する必要があるたびに新しいスレッドオブジェクトを作成するには、コストがかかります。スレッドプールでは、非同期で実行したいタスクをタスクキューに追加するだけで、スレッドプールは、対応するタスクに使用可能なスレッドがある場合はそれを割り当てます。タスクが完了するとすぐに、現在利用可能なスレッドが別のタスクを要求します(残りがあると仮定します)。
スレッドプールは、実際に必要な数よりも多くのスレッドを作成または破棄することを回避するのに役立ちます。
スレッドのキューとタスクのキューを持つクラスを作成することから始めます。次に、タスクをタスクキューに追加し、そこから先に進むメソッドを実装します。もちろん、スレッドプールで許可される最大スレッド数を設定できるようにする必要もあります。
回答
実際の例;
- 機能:オペレーティングシステム
- セクション:アプリケーション
- 人:スレッド
そこに施設があります12人が働いています。この施設には3つのセクションがあります。キッチン、トイレ、セキュリティ。スレッドプール技術を使用しない場合は、そのように機能します。12人全員が会議室に立ち、新しい顧客が施設に来てタスクを要求した場合は、グループに分けて送信します。仕事を終えて会議室に戻りますが、任務に就く前に準備段階があります。正しい制服を着て、特定のデバイスを装備し、そのセクションに歩いて行き、仕事を終えて戻ってくる必要があります。仕事を終える(スレッドが終了する)たびに、会議室に戻り、制服を脱ぎ、機器を取り出し、次の仕事を待つ必要があります。これらは、スレッドコンテキストの作成、メモリ割り当て、OSによる情報の追跡を指します。OSが新しいスレッドのニーズを再編成するには時間がかかりすぎます。
スレッドプールを使用している場合は、早朝に6人をキッチンに、2人をトイレに割り当て、セキュリティに4人。したがって、彼らは1日に1回だけ準備をします。キッチンに客がいない場合でも、4人がアイドリング状態で次のタスクに対応します。キッチンが閉まる(アプリが終了する)まで、会議室に戻る必要はありません。これらの4人は、キッチンアプリプールにいて、すぐにサービスを提供する準備ができています。しかし、キッチンは時々アイドル状態になる可能性があるため、彼らが一日中働いていると約束することはできません。同じ論理がトイレとセキュリティにも当てはまります。
最初のシナリオでは、タスクにスレッドを無駄にすることはありませんが、タスクごとにすべてのスレッドを準備するにはかなりの時間がかかります。 2つ目は、事前にスレッドを準備するため、すべてのタスクにすべてのスレッドを使用することを保証することはできませんが、OSはほとんどの場合、スレッドを大幅に最適化するため、安全に信頼できます。
回答
マルチスレッドアプリケーションでは、スレッドプールは、アプリケーションで使用できる「使用可能なスレッドのプール」です。通常、例えば.NET、それはすべて管理されているので、タスクを割り当てるだけで、スレッドが解放されると、それを実行します。したがって、スレッドプールを実装するには、タスクごとに明示的なスレッドを作成せずに、タスクがフリースレッドによって自動的に実行されるという概念を作成することを期待します。