C#的Socket.Connected属性,返回的是上次IO操作时的连接状态。如果之后连接被断开,访问这个属性依然会返回true,因此不能使用这个属性来判断实时连接状态。
C#还提供了一个Poll(int microSeconds, SelectMode mode)方法。如果mode参数定义为SelecMode.SelectRead时,这个方法在以下情况下会返回true:
- 调用了Listen(即Socket处于监听模式)并且有挂起的连接
- 有数据可以读取
- 连接被关闭、重置或终止
因此,在客户端模式下,调用Socket.Poll(timeout, SelectMode.SelectRead),会出现以下结果:
- 如果连接没有断开,并且没有数据等待接收(即Socket.Available == 0) ,返回false
- 如果连接没有断开,并且有数据等待接收,返回true
- 如果连接已断开,返回true
所以,进行以下判断:
!socket.Poll(timeout, SelectMode.SelectRead) || socket.Available > 0
返回结果为true时,即表示连接未断开,否则连接已断开。