inputstream读取数据不全

TCP通讯使用定长报文。

格式:

请求 :6byte(表示后续报文长度len)+ byte[len]

响应: 6byte(表示后续报文长度len)+ byte[len]

从响应inputstream里按长度头里收到的len继续接收数据,发现有接收不全的情况。

通讯程序大概这样:

Socket socket = null;
InputStream inputStream = null;
OutputStream outputStream = null;
byte[] data = {};//要发送的数据
try {
    //创建Socket对象
    socket=new Socket(host,port);
    //根据输入输出流和服务端连接
    outputStream=socket.getOutputStream();//获取一个输出流,向服务端发送信息
    //补充长度头为6位字符串
    String lenString = PadLen(data.length,6);
    //发送长度头
    outputStream.write(lenString.getBytes());
    //发送数据
    outputStream.write(data);
    outputStream.flush();
    socket.shutdownOutput();//关闭输出流
    //获取一个输入流,接收服务端的信息
    inputStream=socket.getInputStream();
    
    //接收长度头
    byte[] len = new byte[6];
    inputStream.read(len);
    
    //按长度头数据接收实际数据
    int bodylen = Integer.parseInt(new String(len));
    byte[] reqData = new byte[bodylen];
    /**
     !!!就是这一步有问题,根据头指定长度继续接收,发现接收不全!!!
    */
    int readLen =inputStream.read(reqData);

    //关闭相对应的资源
    inputStream.close();
    outputStream.close();
    socket.close();
} catch (Exception e) {
    logger.error("通讯异常",e);
}

就是按响应长度头接收实际数据时,一般数据长度每问题,当实际长度比较大,超过1万字节,实际在按长度接收,接收到长度只有6000多字节。不知为什么。百度说有TCP分包发送啥的也不懂。

最后解决方法,直接使用common-io包里的工具方法,处理流。不按长度接收了。

byte[] recvData = IOUtils.toByteArray(inputStream);

IOUtils.toByteArray方法的处理方式大致这样(2.6版本源码)

InputStream input;
//新建一个输出流
ByteArrayOutputStream output = new ByteArrayOutputStream();
/**
* copy(input, output);
将input输入流中数据复制到构造的输出流中
*/
long count = 0;
int n;
byte[] buffer = new byte[4096];
//循环读取到buffer
while (-1 != (n = input.read(buffer))) {
    output.write(buffer, 0, n);
}
//转换成byte array
return output.toByteArray();
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值