【问题标题】:Java stream of byte. Read operation sometimes doesn't read what was writtenJava 字节流。读取操作有时不会读取写入的内容
【发布时间】:2015-02-21 00:09:51
【问题描述】:

我正在尝试使用自动重复请求策略实现通信系统。我使用三个类:Transmitter、Channel、Receiver。我有消息(窗口)的最大字节数。但是当我收到发送的字节时,有时我收到的字节数比窗口少。为什么? 我的代码是这样的:

发射器

int n = 0;
int remaining, length;
while (n<channelBytes.length) {
     remaining = channelBytes.length-n;
     length = (remaining<window)? remaining : window;
     outputStream.write(channelBytes,n,length);
     // wait for the ack
     byte[] b = new byte[4];
     channel.socket().setSoTimeout(2000);
     inputStream.read(b);
     n += ByteBuffer.wrap(b).getInt();
}

频道

bytes = new byte[SystemModel.WINDOW];
while(true) {
    // receive from Tx
    upInputStream.read(bytes);
    // insert channel error
    insertError(bytes);
    Thread.sleep(propagationDelay + transmissionDelay);
    // send bytes to Rx
    downOutputStream.write(bytes);
    // wait for the ack from Rx
    clientChannelDown.socket().setSoTimeout(2000);
    byte[] ack = new byte[4];
    downInputStream.read(ack);
    // send ack to Tx
    upOutputStream.write(ByteBuffer.allocate(4).put(ack).array());
}

接收者

byte[] b = new byte[SystemModel.WINDOW];
while (true) {
    try {
        int received = inputStream.read(b);
        channelCoding.decodePartially(b);                                        
    }catch (SocketTimeoutException te){  
        break;
    } catch (IOException e) {
        e.printStackTrace();
    } catch (DataFormatException e) {
        // send ack
        int ack = Integer.parseInt(e.getMessage());
        try {
            outputStream.write(ByteBuffer.allocate(4).putInt(ack).array());
        } catch (IOException e1) {
            e1.printStackTrace();
        }
    }
}

在接收器中,字节数组“b”并不总是窗口的长度。

【问题讨论】:

    标签: java stream byte inputstream outputstream


    【解决方案1】:

    无效代码。请参阅 Javadoc。 InputStream.read(byte[] [,...]) 没有义务传输超过一个字节,并且在不将结果存储到变量中的情况下调用它是无效的。如果您期望超过一个字节,则必须循环,或使用DataInputStream.readFully().

    Java 中复制流的规范方法如下:

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

    ByteBuffersChannels 如下:

    while (in.read(buffer) > 0 || buffer.position() > 0)
    {
        buffer.flip();
        out.write(buffer);
        buffer.compact();
    }
    

    如果编码正确,则无需在网络代码中插入睡眠。

    电子与工程

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-01-03
      相关资源
      最近更新 更多