如何识别Java套接字中的EOF?

如何识别Java套接字中的EOF?,java,http,sockets,eof,Java,Http,Sockets,Eof,我想识别Java套接字中数据流的结尾。当我运行下面的代码时,它只是卡住并继续运行(它在值10处卡住) 我还想让程序下载二进制文件,但最后一个字节总是不同的,所以我不知道如何停止while(实际上) 谢谢你的提示 您应该使用现有的HTTP库。看 您的代码按预期工作。服务器未关闭连接,dataBuffer永远不会变成-1。这是因为默认情况下,HTTP 1.1中的连接保持活动状态。使用HTTP 1.0,或在请求中放入连接:关闭头 例如: out.write("GET "+ path +" HTTP/1

我想识别Java套接字中数据流的结尾。当我运行下面的代码时,它只是卡住并继续运行(它在值
10
处卡住)

我还想让程序下载二进制文件,但最后一个字节总是不同的,所以我不知道如何停止while(实际上)

谢谢你的提示

  • 您应该使用现有的HTTP库。看
  • 您的代码按预期工作。服务器未关闭连接,
    dataBuffer
    永远不会变成
    -1
    。这是因为默认情况下,HTTP 1.1中的连接保持活动状态。使用HTTP 1.0,或在请求中放入
    连接:关闭
  • 例如:

    out.write("GET "+ path +" HTTP/1.1\r\nHost: "+ host +"\r\nConnection: close\r\n\r\n");
    out.flush();
    
    int dataBuffer;
    while ((dataBuffer = connection.getInputStream().read()) != -1) 
       System.out.print((char)dataBuffer);
    
    out.close();
    
  • 您应该使用现有的HTTP库。看
  • 您的代码按预期工作。服务器未关闭连接,
    dataBuffer
    永远不会变成
    -1
    。这是因为默认情况下,HTTP 1.1中的连接保持活动状态。使用HTTP 1.0,或在请求中放入
    连接:关闭
  • 例如:

    out.write("GET "+ path +" HTTP/1.1\r\nHost: "+ host +"\r\nConnection: close\r\n\r\n");
    out.flush();
    
    int dataBuffer;
    while ((dataBuffer = connection.getInputStream().read()) != -1) 
       System.out.print((char)dataBuffer);
    
    out.close();
    

    实际上,您的代码不正确

    在HTTP 1.0中,每个连接都是关闭的,因此客户端可以检测输入何时结束

    在具有持久连接的HTTP 1.1中,底层TCP连接保持打开状态,因此客户端可以通过以下两种方式之一检测输入何时结束:

    1) HTTP服务器会放置一个
    内容长度
    头,指示响应的大小。客户机可以使用它来理解何时已完全读取响应

    2) 响应以
    Chunked Encoding
    发送,这意味着它以块的形式出现,并以每个块的大小为前缀。使用此信息的客户机可以根据服务器接收的数据块构造响应

    您应该使用HTTP客户机库,因为实现通用HTTP客户机并不简单(我可以这么说)

    为了在发布的代码中更具体,您应该遵循上述方法之一

    此外,由于HTTP是一种以行终止的协议,所以您应该读取行

    例如:

    BufferedReader in =new BufferedReader(new InputStreamReader( Connection.getInputStream() ) );
    String s=null;
    while ( (s=in.readLine()) != null)  {
    //Read HTTP header
         if (s.isEmpty()) break;//No more headers
       }
    }
    
    通过发送khachik建议的
    连接:close
    ,可以完成任务(因为关闭连接有助于检测输入的结束),但性能会变得更差,因为对于每个请求,您都会启动一个新连接


    这当然取决于你想做什么(如果你在乎或不在乎)

    实际上你的代码是不正确的

    在HTTP 1.0中,每个连接都是关闭的,因此客户端可以检测输入何时结束

    在具有持久连接的HTTP 1.1中,底层TCP连接保持打开状态,因此客户端可以通过以下两种方式之一检测输入何时结束:

    1) HTTP服务器会放置一个
    内容长度
    头,指示响应的大小。客户机可以使用它来理解何时已完全读取响应

    2) 响应以
    Chunked Encoding
    发送,这意味着它以块的形式出现,并以每个块的大小为前缀。使用此信息的客户机可以根据服务器接收的数据块构造响应

    您应该使用HTTP客户机库,因为实现通用HTTP客户机并不简单(我可以这么说)

    为了在发布的代码中更具体,您应该遵循上述方法之一

    此外,由于HTTP是一种以行终止的协议,所以您应该读取行

    例如:

    BufferedReader in =new BufferedReader(new InputStreamReader( Connection.getInputStream() ) );
    String s=null;
    while ( (s=in.readLine()) != null)  {
    //Read HTTP header
         if (s.isEmpty()) break;//No more headers
       }
    }
    
    通过发送khachik建议的
    连接:close
    ,可以完成任务(因为关闭连接有助于检测输入的结束),但性能会变得更差,因为对于每个请求,您都会启动一个新连接



    当然,这取决于您正在尝试做什么(如果您介意或不介意)

    也许我在这里错了,但这应该会发生,因为服务器没有关闭连接。HTTP 1.1默认情况下是
    保持活动状态
    。您不将现有库用于HTTP的任何特定原因?以及修复请求上连接头的问题;)该程序应该是一个小代理(不仅适用于HTTP)。@user961912,您可以
    java.net.URL
    用于常见URL。也许我在这里错了,但这应该发生,因为服务器没有关闭连接。HTTP 1.1默认情况下是
    保持活动状态
    。您不将现有库用于HTTP的任何特定原因?以及修复请求上连接头的问题;)该程序应该是一个小代理(不仅适用于HTTP)。@user961912,您可以
    java.net.URL
    用于常见URL。标题以空行结尾。读取直到readLine()返回null与他开始时遇到的问题完全相同。他应该一直读到s.length()为零。@EJP:在你否决投票之前,你应该仔细阅读答案。我说过他必须使用HTTP头来查找内容长度。代码示例强调他可以逐行解析HTTPline@user384706(a)你没有任何证据表明是谁否决了该职位;(b) 我仔细阅读了你的帖子,发现了一个缺陷并提出了更正。@EJP:好的,关于否决票,你是对的。从我的角度来看,认为你这样做可能不公平。关于缺陷,我不同意,那么你错了。您不知道自己的代码是如何工作的。标头以空行结尾。读取直到readLine()返回null与他开始时遇到的问题完全相同。他应该一直读到s.length()为零。@EJP:在你否决投票之前,你应该仔细阅读答案。我说过他必须使用HTTP头来查找内容长度。代码示例强调他可以逐行解析HTTPline@user384706(a)你没有任何证据表明是谁否决了该职位;(b) 我仔细阅读了你的帖子,足以观察佛罗里达州的情况