var raw = socket.getInputStream();
var buffered = new BufferedInputStream(raw);
byte[] b = new byte[1000];
buffered.read(b); // actually reads 4000 bytes into buffer, giving 1000 of them.
// 3000 left in the buffer!
byte[] c = new byte[2000];
buffered.read(c); // works fine and never touches raw. Can't throw.
byte[] d = new byte[2000];
buffered.read(d); // 'mixed mode'
2条答案
按热度按时间wyyhbhjk1#
如果没有好消息,数据就会丢失。
5t7ly7z52#
这个理论有道理吗?客户端是否需要保持连接打开,以便服务器从输入流中完全读取字节?
不。
只要
BufferedInputStream
缓冲区中有字节,任何调用read()
/read(byte[])
/read(byte[], int, int)
只会从缓冲区中提供数据,甚至不会触及底层的inputstream。只要你不碰输入流,它就不能从晴朗的蓝天中抛出异常。您需要在实际的socket inputstream上调用一些东西(可以是read、close、flush、write-something),以便引发异常。
可能发生的是混合模式操作:您调用例如:
在这里,在“混合模式”的情况下,前1000个字节由缓冲区填充,但是
raw.available()
调用(源:bufferedinputstream.java的实际源代码);如果返回一个非零数,则直接从原始数据中获取更多的数据;如果是0,read()
刚刚回来(read()
没有义务读取所有请求的字节;它只需要[a]读取至少1,并且[b]返回它读取了多少;通常你想要readNBytes
相反)。然而,
in.available()
被允许扔。如果有,瞧。但是,正常的tcp关闭不会导致timeoutexceptions。
更可能的情况是:您的代码处理数据的速度不够快。发送实体在某个时候已经厌倦了这一切,拒绝继续让您占用文件句柄,只是挂断了您的连接。如果您已经在使用缓冲区,可能中间有一些网络设备的速度非常慢,或者服务器的配置对您的网络连接速度有着不切实际的期望。