BufferedReader没有读取第二个输出

时间:2017-11-17 20:32:05

标签: java sockets bufferedreader printwriter

我正在为小游戏开发客户端。使用套接字,我正在使用BufferedReaderBufferedReader类解析请求和响应。

我遇到的问题是第二次使用public class BotClient { private final Socket socket; private final PrintWriter writer; private final BufferedReader reader; public BotClient(final String gameId, final String botName) throws IOException { this.writer = new PrintWriter(socket.getOutputStream(), true); this.reader = new BufferedReader(new InputStreamReader(socket.getInputStream())); } //Code that connects client to server. Works successfully. public void sendGameRequest() { try { //This first is the FIRST request to server. This works SUCCESSFULLY. writer.println("GET " + "/playerInfo/?gameId=" + gameId + "&playerName=" + botName + " HTTP/1.0\r\n"); reader.lines().forEach(System.out::println); // This will output game response successfully. //Now the problem occurs below here. I could do the same request but won't get an output. writer.println("GET " + "/playerInfo/?gameId=" + gameId + "&playerName=" + botName + " HTTP/1.0\r\n"); reader.lines().forEach(System.out::println); //EMPTY PRINT // The above is EXACTLY the same request however this prints out nothing. 时(服务器的第二次响应)。

示例:

"phd", "undergrad"

这可能是什么问题,解决这个问题的最佳方法是什么?

4 个答案:

答案 0 :(得分:0)

分析

我认为第二个writer.println()方法调用不会发生,因为声明:

reader.lines().forEach(System.out::println);

描述了从流中读取行,而未到达流的末尾(即当套接字关闭时)。

答案 1 :(得分:0)

如我所见,这是一个HTTP请求:

writer.println("GET " + "/playerInfo/?gameId=" + gameId + "&playerName=" + botName + " HTTP/1.0\r\n");

可能是在第一次请求后,远程梨关闭了连接。因此,每次发送请求时,都应该打开连接,发送请求,等待并接收响应并关闭套接字。

这是本书中的一个提取器:David Gourley和Brian Totty的 Http权威指南enter image description here

在发送第二个请求之前检查套接字是否已打开,如果没有,请再次打开它并重复进程以发送请求。

答案 2 :(得分:0)

reader.lines()只提供一个流式视图,相当于重复调用reader.readLine(),直到到达文件末尾。一旦你读完整个流,就没有更多的行可供阅读。

您需要存储这些线条。最简单的方法是将它们收集到List中:

List<String> lines = reader.lines().collect(Collectors.toList());
lines.forEach(System.out::println);

关于InputStreamReader的警告:由于您没有提供字符集,它将使用系统的默认字符集。这意味着您的代码在Windows上的运行方式与在其他操作系统上的运行方式不同; Windows机器可能无法与非Windows机器通信。

要使其在所有系统上以相同方式运行,请指定显式字符集:

    this.reader = new BufferedReader(new InputStreamReader(socket.getInputStream(), StandardCharsets.UTF_8));

答案 3 :(得分:0)

文档says

  

在执行终端流操作期间,不得操作阅读器。否则,终端流操作的结果是未定义的。执行终端流操作后,无法保证读者将处于读取下一个字符或行的特定位置。