如何在客户端之间连续发送消息



我有一个简单的客户端/服务器应用程序,它将2个客户端分组,并使它们相互通信,如果第三个客户端连接,它将无法与其他2个客户端通信,但它将创建另一个由2个客户端组成的组,依此类推…然而,当我从客户端发送消息时,问题会出现,它不会立即将消息发送给另一个客户端相反,它等待第一个客户端输入,也等待第二个客户端输入并且只有当两个客户端都输入了一个输入时,它才将它们发送给彼此。任何帮助都会被告知。

服务器:

public class ChatServer {
Socket previousSocket = null;

public static void main(String[] args) throws Exception {
ServerSocket serverSocket = new ServerSocket(9001);
System.out.println("The chat server is running.");
Socket previousSocket = null;
while (true) {
Socket newSocket = serverSocket.accept();

/**
* if (previousSocket == null) occurs if only 1 client is connected and its being set as a previousSocket
* and we wait for a second client to connect so meanwhile nothing happens
* 
* if second clients joins in we can start communicating in groups of 2
*/

if (previousSocket == null) { 
previousSocket = newSocket;
} else {
new Handler(previousSocket, newSocket).start();
new Handler(newSocket, previousSocket).start();
previousSocket = null;
}
}
}

private static class Handler extends Thread {
private String name;
private Socket socket;
private Socket peerSocket;
private DataInputStream in;
private DataOutputStream out;
public Handler(Socket socket, Socket peerSocket) {
this.socket = socket;
this.peerSocket = peerSocket;
}
public void run() {
try {
while (true) {
in = new DataInputStream(socket.getInputStream());
out = new DataOutputStream(peerSocket.getOutputStream());



try {
String input = in.readUTF();

out.writeUTF(input);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

}
}
}

客户:

public class ChatClient {
public static void main(String[] args) throws UnknownHostException, IOException {
new ChatClient();
}

public ChatClient() throws UnknownHostException, IOException  {
Socket socket = new Socket("127.0.0.1", 9001);

System.out.println("You can start typing:");

while(true) {


Scanner scanner = new Scanner(System.in);

Thread input = new Thread() {
@Override
public void run() {
while(true) {
try {
DataInputStream inputStream = new DataInputStream(socket.getInputStream());

while(scanner.hasNextLine()) {
String message = scanner.nextLine();

System.out.println(message);

//reading messages from server
String received = inputStream.readUTF();
System.out.println(received);
}
} catch (IOException e) {

e.printStackTrace();
}
}
}
};
input.start();

Thread output = new Thread() {
public void run() {
try {
DataOutputStream outputStream = new DataOutputStream(socket.getOutputStream());
while(scanner.hasNextLine()) {
String message = scanner.nextLine();

if(message.equalsIgnoreCase("quit")) {
socket.close();
break;
}

outputStream.writeUTF(message);
}
} catch (IOException e) {

e.printStackTrace();
}


};
};
output.start();

}
}
}

在客户端从服务器读取时,删除顶级while循环并删除scanner.nextLine()
我已经在下面更新了您的客户端代码,这应该可以正常工作。

public class ChatClient {
public static void main(String[] args) throws UnknownHostException, IOException {
new ChatClient();
}

public ChatClient() throws UnknownHostException, IOException  {
Socket socket = new Socket("127.0.0.1", 9001);

System.out.println("You can start typing:");


Scanner scanner = new Scanner(System.in);
System.out.println("got it");
Thread input = new Thread() {
@Override
public void run() {
while(true) {
try {
DataInputStream inputStream = new DataInputStream(socket.getInputStream());

while(true) {
//String message = scanner.nextLine();

//System.out.println(message);

//reading messages from server
String received = inputStream.readUTF();
System.out.println(received);
}
} catch (IOException e) {

e.printStackTrace();
}
}
}
};
input.start();

Thread output = new Thread() {
public void run() {
try {
DataOutputStream outputStream = new DataOutputStream(socket.getOutputStream());
while(scanner.hasNextLine()) {
String message = scanner.nextLine();

if(message.equalsIgnoreCase("quit")) {
socket.close();
break;
}

outputStream.writeUTF(message);
}
} catch (IOException e) {

e.printStackTrace();
}


};
};
output.start();
}
}

您需要将客户端中的输入流和输出流分离为两个独立的线程。问题是,在您读取输入之前,您的客户端正在等待扫描仪的输入。扫描程序是一个阻塞调用,所以它需要自己的线程。

此外,您应该将循环中数据流的创建转移到构造函数。。。这将提高你的效率。

最新更新