【问题标题】:Fell into infinite loop while receiving file using datainputstream and bufferedinputstream使用 datainputstream 和 bufferedinputstream 接收文件时陷入无限循环
【发布时间】:2011-10-05 03:16:02
【问题描述】:

我正在尝试构建一个使用 DataInputStream 和 BufferedInputStream 从客户端接收文件的服务器程序。

这是我的代码,它陷入了无限循环,我认为这是因为没有使用 available() 但我不太确定。

DataInputStream din = new DataInputStream(new BufferedInputStream(s.getInputStream()));
//s is socket that connects fine
fos = new FileOutputStream(directory+"/"+filename);

byte b[] = new byte[512]; 
int readByte = din.read(b);
while(readByte != 1){
    fos.write(b);
    readByte = din.read(b);
    //System.out.println("infinite loop...");
}

谁能告诉我为什么它会陷入无限循环?如果是因为没有使用 available ,请告诉我如何使用它?我实际上用谷歌搜索,但我对用法感到困惑。非常感谢

【问题讨论】:

    标签: java network-programming bufferedinputstream datainputstream


    【解决方案1】:

    我想你想做while(readByte != -1)。请参阅documentation(-1 表示没有更多可阅读的内容)。

    回复评论

    这对我有用:

    FileInputStream in = new FileInputStream(new File("C:\\Users\\Rachel\\Desktop\\Test.txt"));
    DataInputStream din = new DataInputStream(new BufferedInputStream(in));
    FileOutputStream fos = new FileOutputStream("C:\\Users\\Rachel\\Desktop\\MyOtherFile.txt");
    
    byte b[] = new byte[512]; 
    while(din.read(b) != -1){
        fos.write(b);
    }
    
    System.out.println("Got out");
    

    【讨论】:

    • 哎呀.. 我明白了。但即使我改成 while(readByte != -1) 我仍然陷入无限循环....
    • 我在 BufferedInputStream 之上使用了 DataInputStream,而不是 FileInputStream。我复制了你的,除了 FileInputStream 部分,我仍然陷入无限循环。我认为问题在于,由于服务器正在等待缓冲区被填充,它处于有限循环中,因为对于文件的最后一部分,不能保证 byte[512] 将被填充。我假设我需要使用 available() 方法.. 但对此不太确定
    • 我修复了无限循环!我不得不使用 available() 方法但是谢谢你 Rachel!
    • 很高兴您修复了它。 :) 回答您自己的问题并将其标记为答案可能是个好主意,以防每个人都遇到相同的问题并找到您的问题。
    【解决方案2】:

    正如 Rachel 指出的,DataInputStream 上的read method 返回成功读入的字节数,如果已到达末尾,则返回-1。循环直到结束的惯用方式是while(readByte != -1),而您错误地使用了1。如果永远不会读取恰好 1 个字节,那么这将是一个无限循环(一旦到达流的末尾,readByte 将永远不会从 -1 更改)。如果偶然有一次迭代恰好读取了 1 个字节,那么这实际上会提前终止,而不是进入无限循环。

    【讨论】:

      【解决方案3】:

      您的问题已得到解答,但此代码存在另一个问题,已在下面更正。规范的流复制循环如下所示:

      while ((count = in.read(buffer)) > 0)
      {
        out.write(buffer, 0, count);
      }
      

      【讨论】:

      • 我尝试了你的代码,但仍然陷入无限循环。这是我所做的 while ((readByte=din.read(b) >0){ fos.write(b, 0, readByte}
      • @在他的步骤中,除非输入无限长,否则代码不可能无限循环。如果发件人没有关闭连接,它肯定会在数据结束时阻塞 - 这就是你的意思吗?
      • 我在 BufferedInputStream 之上使用了 DataInputStream,可能缓冲区正在等待填充。我认为这会导致无限循环,但不太确定。
      • 我修好了!我不得不使用 available() 方法!谢谢EJP
      • @in His Steps 更可能您应该使用单独的线程来读取套接字。 available() 并没有多大用处。或者,当您阅读了整个当前消息时,该协议会告诉您。
      猜你喜欢
      • 2020-05-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-03-17
      • 2021-02-15
      相关资源
      最近更新 更多