如何识别 Java 套接字中的 EOF?
我想识别 Java 套接字中的数据流结束。当我运行下面的代码时,它只是卡住并继续运行(它卡在值10
)。
我还希望程序下载二进制文件,但最后一个字节总是不同的,所以我不知道如何停止 while (实用地)。
String host = "example.com";
String path = "/";
Socket connection = new Socket(host, 80);
PrintWriter out = new PrintWriter(connection.getOutputStream());
out.write("GET "+ path +" HTTP/1.1\r\nHost: "+ host +"\r\n\r\n");
out.flush();
int dataBuffer;
while ((dataBuffer = connection.getInputStream().read()) != -1)
System.out.println(dataBuffer);
out.close();
感谢您的任何提示。
I want to recognize end of data stream in Java Sockets. When I run the code below, it just stuck and keeps running (it stucks at value 10
).
I also want the program to download binary files, but the last byte is always distinct, so I don't know how to stop the while (pragmatically).
String host = "example.com";
String path = "/";
Socket connection = new Socket(host, 80);
PrintWriter out = new PrintWriter(connection.getOutputStream());
out.write("GET "+ path +" HTTP/1.1\r\nHost: "+ host +"\r\n\r\n");
out.flush();
int dataBuffer;
while ((dataBuffer = connection.getInputStream().read()) != -1)
System.out.println(dataBuffer);
out.close();
Thanks for any hints.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
实际上您的代码不正确。
在 HTTP 1.0 中,每个连接都会关闭,因此客户端可以检测到输入何时结束。
在具有持久连接的 HTTP 1.1 中,底层 TCP 连接保持打开状态,因此客户端可以通过以下 2 种方式之一检测输入何时结束:
1) HTTP 服务器放置一个
Content-Length
标头,指示响应的大小。客户端可以使用它来了解响应何时已被完全读取。2) 响应以分块编码的形式发送,这意味着它以块的形式发送,并以每个块的大小为前缀。使用此信息的客户端可以根据服务器接收到的块构建响应。
您应该使用 HTTP 客户端库,因为实现通用 HTTP 客户端并不简单(我可以这么说)。
要具体说明您发布的代码,您应该遵循上述方法之一。
此外,您应该按行阅读,因为 HTTP 是行终止协议。
即:
通过按照 khachik 的建议发送
Connection: close
,完成工作(因为连接的关闭有助于检测输入的结束),但性能会变得更差,因为对于每个请求开始一个新的连接。当然,这取决于您想要做什么(如果您关心或不关心)
Actually your code is not correct.
In HTTP 1.0 each connection is closed and as a result the client could detect when an input has ended.
In HTTP 1.1 with persistent connections, the underlying TCP connection remains open, so a client can detect when an input ends with 1 of the following 2 ways:
1) The HTTP Server puts a
Content-Length
header indicating the size of the response. This can be used by the client to understand when the reponse has been fully read.2)The response is send in
Chunked-Encoding
meaning that it comes in chunks prefixed with the size of each chunk. The client using this information can construct the response from the chunks received by the server.You should be using an HTTP Client library since implementing a generic HTTP client is not trivial (at all I may say).
To be specific in your code posted you should have followed one of the above approaches.
Additionally you should read in lines, since HTTP is a line terminated protocol.
I.e. something like:
By sending a
Connection: close
as suggested by khachik, gets the job done (since the closing of the connection helps detect the end of input) but the performance gets worse because for each request you start a new connection.It depends of course on what you are trying to do (if you care or not)
dataBuffer
永远不会变成-1
。发生这种情况是因为默认情况下 HTTP 1.1 中的连接保持活动状态。使用 HTTP 1.0,或将Connection: close
标头放入请求中。例如:
dataBuffer
never becomes-1
. This happens because connections are kept alive in HTTP 1.1 by default. Use HTTP 1.0, or putConnection: close
header in your request.For example: