我已经阅读了java文档和许多相关问题,但是不确定是否可以保证工作:
我在专用线程上有一个DatainputStream,该线程不断地从非常有效的连接中读取已知字节大小的少量数据。我想在流动不活动时提醒用户(即网络下降),因此我已经实现了以下内容:
...
streamState = waitOnStreamForState(stream, 4);
int i = stream.readInt();
...
private static int
waitOnStreamForState(DataInputStream stream, int nBytes) throws IOException {
return waitOnStream(stream, nBytes, STREAM_ACTIVITY_THRESHOLD, STREAM_POLL_INTERVAL)
? STREAM_STATE_ACTIVE
: STREAM_STATE_INACTIVE;
private static boolean
waitOnStream(DataInputStream stream, int nBytes, long timeout, long pollInterval) throws IOException {
int timeWaitingForAvailable = 0;
while( stream.available() < nBytes ){
if( timeWaitingForAvailable >= timeout && timeout > 0 ){
return false;
}
try{
Thread.sleep(pollInterval);
}catch( InterruptedException e ){
Thread.currentThread().interrupt();
return (stream.available() >= nBytes);
}
timeWaitingForAvailable += pollInterval;
}
return true;
}
可用文档()解释:
返回可以从此输入流中读取(或跳过)的字节数的估计,而不会阻止下一个呼叫者的下一个呼叫者此输入流的方法下一个呼叫者可能是同一线程或其他线程。单个字节的单个读取或跳过不会阻塞,但可能会读取或跳过字节更少。
这是否意味着下一个读取(Inside ReadInt())可能仅读取2个字节,然后随后的读取以完成整数可以阻止吗?我意识到ReadInt()是流的一种方法"称为Next"的方法,但我认为它必须在读取呼叫上循环,直到获得4个字节,并且文档不会提及后续呼叫。在上面的示例中,即使waitinstreamforstate(stream,4)返回stream_state_active,readint()调用仍然可以阻止?
(是的,我意识到我的超时机制不是精确的)
这是否意味着下一个读取(Inside readint())可能仅读取2个字节,然后随后的读取以完成整数可以阻止吗?
这就是它所说的。但是,至少下一个read()
不会阻止。
我意识到readint()是流的一种"称为Next"的方法,但我认为它必须在读取呼叫上循环,直到获得4个字节,并且文档不提及后续呼叫。在以上示例中
这就是它所说的。
例如,考虑SSL。您可以说有可用的数据,但是您不能实际减少它的情况下判断多少,因此JSSE实施是免费的:
- 始终从
available()
返回0(这是它过去做的) - 如果固定插座的输入流具有
available() > 0
,则始终返回1,否则零> - 返回基础套接字输入流的
available()
值,并依靠此措辞,如果实际的明文数据较小,则将其摆脱困境。(但是,如果密码数据完全由握手消息或警报组成,则正确的值可能仍然为零。)
但是,您不需要任何一个。您需要的只是通过Socket.setSoTimeout()
设置的读取超时,而SocketTimeoutException
的catch
。在我看来,随着时间的流逝,available()
的正确用途很少,越来越少。您当然应该不是浪费时间致电sleep()
。