gpt4 book ai didi

java - 客户端似乎已连接但服务器未接受它

转载 作者:行者123 更新时间:2023-11-30 01:46:07 25 4
gpt4 key购买 nike

我试图说明套接字服务器和客户端的一个问题,其中服务器应该一次只处理一个客户端,因此多个客户端必须互相等待。

这是我的服务器类。我可以接受来自一个客户端的连接,读取一些字符串,将其大写并将其发回。然后将为下一个客户提供服务。因此,如果我启动多个客户端,第一个客户端将连接,但其余客户端必须等待服务器再次调用accept()。这就是假设。

System.out.println("Starting server...");

try {
ServerSocket welcomeSocket = new ServerSocket(2910);

while(true) {
Socket socket = welcomeSocket.accept();
System.out.println("client connected");

ObjectInputStream inFromClient = new ObjectInputStream(socket.getInputStream());
String o = (String)inFromClient.readObject();
System.out.println("Received: " + o);

String answer = o.toUpperCase();

ObjectOutputStream outToClient = new ObjectOutputStream(socket.getOutputStream());
System.out.println("Sending back: " + answer);
outToClient.writeObject(answer);
}
} catch (IOException | ClassNotFoundException e) {
// socket stuff went wrong
}

这是我的客户端代码:

try {
Socket socket = new Socket("localhost", 2910);
System.out.println("Connected to server");
ObjectOutputStream outToServer = new ObjectOutputStream(socket.getOutputStream());
Scanner in = new Scanner(System.in);
System.out.println("What to send?");
String toSend = in.nextLine();
System.out.println("Sending " + toSend);
outToServer.writeObject(toSend);

ObjectInputStream inFromServer = new ObjectInputStream(socket.getInputStream());
String o = (String)inFromServer.readObject();

System.out.println("Received: " + o);
} catch (IOException | ClassNotFoundException e) {}

我创建与服务器的连接,然后从控制台读取。第一个客户端应该连接成功,然后打印出“已连接到服务器”。其他客户端应该会卡在创建套接字上,直到服务器调用accept()。至少我是这么想的。

但是我的所有客户端都打印出“已连接到服务器”,我可以在所有客户端的控制台中键入内容,并将其发送到服务器。然后,服务器仍将一次响应一个客户端。

但是为什么在我的服务器接受连接之前我的客户端代码会从初始连接继续前进? java 8 中似乎是这种情况,但现在我使用的是 java 11。

最佳答案

如果您想阻止操作系统在调用accept() 之前接受多个连接,请将backlog 设置为1。

否则,在调用accept()之前,操作系统通常最多接受5个连接。客户端相信已连接,因为它们确实是在 TCP/IP 级别连接的。

<小时/>

查看文档:

公共(public)ServerSocket(int 端口, int 积压) 抛出 IOException创建服务器套接字并将其绑定(bind)到指定的本地端口号,并具有指定的积压。端口号 0 表示端口号是自动分配的,通​​常是从临时端口范围中分配的。然后可以通过调用 getLocalPort 来检索此端口号。传入连接指示(连接请求)的最大队列长度设置为 backlog 参数。如果队列已满时连接指示到达,则连接被拒绝。

如果应用程序指定了服务器套接字工厂,则会调用该工厂的 createSocketImpl 方法来创建实际的套接字实现。否则会创建一个“普通”套接字。

如果有安全管理器,则会以端口参数作为参数调用其 checkListen 方法,以确保允许该操作。这可能会导致 SecurityException。 backlog 参数是套接字上请求的最大挂起连接数。其确切的语义是特定于实现的。特别地,实现可以施加最大长度或者可以选择完全忽略该参数。提供的值应大于 0。如果它小于或等于 0,则将使用特定于实现的默认值。

参数:port - 端口号,或 0 以使用自动分配的端口号。backlog - 请求的传入连接队列的最大长度。

关于java - 客户端似乎已连接但服务器未接受它,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57920167/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com