サーバーは本質的にアイテムのキューであり、クライアントはそのようなアイテムのプロデューサーおよび/またはコンシューマーとして機能します。
サーバーは次のことを行う必要があります。
- put / take リクエストをリッスンし、それに応じて処理します。通常、これにはあまり時間がかかりません。次の要素で構成されます。
- 短い文字列を解析します。
- アン
HashMap.get
; - ロックの取得。
PriorityQueue.poll
またはPriorityQueue.offer
; _
- すべてのクライアントに、すべてのアイテム アクティビティをできるだけ早く通知して、すべてのクライアントが何が起こっているかをリアルタイムで確認できるようにします。
これを設定する最も簡単な方法は、accept
クライアントをスレッド化してから、クライアントごとに 2 つのスレッドを作成することです。
InputStream
リクエストの待機をブロックする を処理するもの。- もう 1 つは
OutputStream
、キューでイベントをリッスンし、情報をクライアントに送信する を処理します。
確かにこれはスケーラブルではなく、クライアントごとに 2 つのスレッドを持つのは無駄に思えます。
また、単一のスレッドを使用することも考えました。
- ソケットのタイムアウトを
read
約 1 秒に設定します。 read
タイムアウトの場合、またはリクエストの処理後に、すべての新しいイベントをクライアントに送信します。- これら 2 つのアクションをループします。
ただし、リクエストとイベントのポーリングも無駄です。
別のアプローチでは、スレッド プールを使用し、上記の 2 つのアクションをそれぞれの に配置しますRunnable
。これらのランナブルは、Executor
. これは、それ以上ではないにしても、同じくらい無駄に思えます。
私はいくつかの 質問を読んでいましたが、ノンブロッキング操作とイベント駆動型サーバーが正しいアプローチであるように思われるため、NIO に興味があります。
上記の設計のいずれかがこのタスクに適していますか、または NIO で取り組む必要がありますか?
数に関して言えば、これは実際のシステムというよりも演習であるため、何千ものクライアントを処理する必要はありませんが、理想的には、パフォーマンスとスケーリングが適切に実行できる必要があります。