我无法弄清楚原因。当服务器向客户端发送字符串时,客户端就可以正常运行。但是当我向我的Client类添加代码以将字符串发送到我的服务器时,它不起作用。帮助
编辑:所以我删除了out.close();在我的Server类中,并用skt.shutdownOutput()替换它;但现在,当我打电话给我的课程时,我得到了:
======================
Server has connected!
Server: Sending message: Test string to show connection between server and client.
Client: Received message: null
Server: Received message: null
为什么?
客户类:
import java.lang.*;
import java.io.*;
import java.net.*;
class Client {
public static void main(String args[]) {
}
//for receiving messages from Server
public void receiveMessage() {
try {
Socket skt = new Socket(InetAddress.getLocalHost().getHostName(), 1234);
BufferedReader in = new BufferedReader(new InputStreamReader(skt.getInputStream()));
//while (!in.ready()) {}
System.out.println("Client: Received message: " + in.readLine()); // Read one line and output it
in.close();
//skt.close(); //maybe delete
} catch (Exception e) {
System.out.print("Client had error receiving message.\n");
}
}
//for sending messages to Server
public void sendMessage(String message) throws IOException {
try {
Socket skt = new Socket(InetAddress.getLocalHost().getHostName(), 1234);
PrintWriter pw = new PrintWriter(skt.getOutputStream());
System.out.println("Client: Sending message: " + message);
pw.print(message);
//skt.close(); //maybe delete
} catch (Exception e) {
System.out.println(e);
System.out.print("Client had error sending message.\n");
}
}
}
服务器类:
import java.lang.*;
import java.io.*;
import java.net.*;
import java.util.concurrent.*;
import java.util.logging.Level;
import java.util.logging.Logger;
public class Server {
String message = "Test string to show connection between server and client.";
public void Open() {
final ExecutorService clientProcessingPool = Executors.newFixedThreadPool(10);
Runnable serverTask = new Runnable() {
@Override
public void run() {
try {
System.out.println("Opening...");
ServerSocket srvr = new ServerSocket(1234);
while (true) {
Socket skt = srvr.accept();
clientProcessingPool.submit(new ClientTask(skt));
}
} catch (Exception e) {
System.out.println(e);
System.out.print("You're opening too many servers in the same location, fool!\n");
}
}
};
Thread serverThread = new Thread(serverTask);
serverThread.start();
}
private class ClientTask implements Runnable {
private final Socket skt;
private ClientTask(Socket skt) {
this.skt = skt;
}
@Override
public void run() {
//for sending messages
System.out.println("======================");
System.out.println("Server has connected!");
PrintWriter out = null;
try {
out = new PrintWriter(skt.getOutputStream(), true);
} catch (IOException ex) {
System.out.println(ex);
System.out.println("Server had error sending message.");
}
System.out.print("Server: Sending message: " + message + "\n");
out.print(message);
//out.close();
try {
skt.shutdownOutput();
} catch (IOException ex) {
Logger.getLogger(Server.class.getName()).log(Level.SEVERE, null, ex);
}
/*
try {
skt.close();
} catch (IOException ex) {
Logger.getLogger(Server.class.getName()).log(Level.SEVERE, null, ex);
}*/
//for receiving messages
//maybe make message procesing method
try {
BufferedReader br = new BufferedReader(new InputStreamReader(skt.getInputStream()));
System.out.println("Server: Received message: " + br.readLine()); // Read one line and output it
//br.close();
//skt.close(); //maybe delete
} catch (Exception e) {
System.out.println("Server had error receiving message.");
System.out.println("Error: " + e);
}
}
}
}
感谢您的任何建议。
答案 0 :(得分:3)
out.print(message);
out.close();
关闭PrintStream
后,您将关闭基础OutputStream
。
getOutputStream()
中Socket
的文档说:
关闭返回的
OutputStream
将关闭相关的套接字。
因此,当您关闭PrintStream
时,也会关闭套接字。仅当您完成当前会话的客户端和服务器之间的所有通信时才关闭流。
您的下一个问题(编辑后)是您没有刷新数据。您的客户端连接,服务器打印,无需刷新,因此数据仍在缓冲区中等待,而不是在流中。像以前一样关闭流也会刷新数据,但是现在您只是将流丢弃,未被刷新的数据将被丢弃。
因此,流关闭,客户端看到指示流结束的null
。
因此,您需要在丢弃流之前刷新数据。
并且服务器报告它已收到null
,因为在其输入流上没有发送任何内容。客户端接收信息然后退出,这会导致套接字关闭,流关闭,服务器看到流末尾。
如果您拨打sendMessage
方法,您会看到几乎相同的内容。流正在写一些东西,但没有人在听它。由于消息很短,服务器不会阻止写入,但没有人在另一侧读取它,它有可能阻止。然后,服务器尝试读取发送给它的内容。但是您的客户端在完成执行并关闭套接字之前不会刷新数据。因此,服务器也会看到null
。