1

私は現在、複数のクライアントが接続するサーバーを作成しています。通信プロトコルは、基本的にサーバーがクライアントにタスクを送信し、タスクが実行されたときにクライアントが応答するというものです。クライアントはサーバーへの接続を維持し、切断しないでください。

現在、各クライアントを処理するための新しいスレッドを開始しています。精神的には、私の現在のソリューションは次のようなものです:(実際にはJava同時実行からのソース)

public class ThreadPerTaskWebServer {
    public static void main(String[] args) throws IOException {
        ServerSocket socket = new ServerSocket(80);
        while (true) {
            final Socket connection = socket.accept();
            Runnable task = new Runnable() {
                public void run() {
                    handleRequest(connection);
                }
            };
            new Thread(task).start();
        }
    }

    private static void handleRequest(Socket connection) {
        // request-handling logic here
    }
}

しかし、エグゼキューターはより安定していて拡張性が高いように見えるので、エグゼキューターを使用したいと思います。したがって、サーバーがクライアントにメッセージを送信できるようにするには、クライアントを実行しているエグゼキューターとは別にクライアントを追跡する必要があります。したがって、クライアントをCopyOnWriteArrayListクライアントのどこに配置し、Serverクラスに次のようなものがある場合:

Socket clientSocket = serverSocket.accept();
// The runnable that takes care of a client 
ClientHandler c = new ClientHandler(clientSocket, this);
// Start executing the ClientHandler
exec.execute(c);
// Add clients to CopyOnWriteArrayList
clients.add(c);

これにより、CopyOnWriteArrayListを反復処理して、すべてのクライアントにコマンドを送信し、切断されたクライアントを削除することができます。これは堅牢なソリューションでしょうか?何らかの理由でランナブルが例外を伝播した場合、エグゼキュータはどうなりますか?

4

2 に答える 2

1

これは堅牢なソリューションでしょうか?

はい、そう思います。固定サイズのプールに適切な数のスレッドを割り当てるか、動的プールを使用する必要があります。

何らかの理由でランナブルが例外を伝播した場合、エグゼキュータはどうなりますか?

コードがをスローするRuntimeExceptionと、コードを実行しているエグゼキュータプールスレッドは停止しますが、プールスレッド数が減少し、サービスがまだシャットダウンされていない場合は別のスレッドが作成されます。したがって、スレッドプールは引き続き適切に動作します。

これにより、CopyOnWriteArrayListを反復処理して、すべてのクライアントにコマンドを送信し、切断されたクライアントを削除することができます。

もちろん、それらへの参照を保存しない限り、切断されたものを削除する必要はありません。そうでなければ、私はこの要件について実際にコメントすることはできません。

于 2012-04-05T19:25:25.580 に答える
1

接続アプローチごとにスレッドを選択し、NIO apiを使用したくない場合は、これが適切なソリューションであると思います。ただし、プールサイズが同時リクエストの数よりも小さい場合は、前のリクエストが終了するまでクライアントが保留になっていることに注意してください。

タスクで例外が発生した場合はどうなりますか。スレッドは終了しますが、エグゼキュータは他のスレッドを作成します。

于 2012-04-05T19:31:09.953 に答える