流不可写异常的可能原因是什么

本文关键字:是什么 异常 | 更新日期: 2023-09-27 18:22:40

当使用C#中的网络流通过TCP序列化自定义对象时,流不可写入异常的可能原因是什么。我正在以数据包的形式发送Mp3数据。帧由Byte[]缓冲区组成。我正在使用二进制格式化程序来序列化对象。

BinaryFormatter.Serialize(NetworkStream,Packet);

客户端播放的带有失真和抖动的Mp3结束了几秒钟,然后出现了上述异常。我正在使用NAudio开源库。

在做这个修改之前,我使用的是

NetworkStream.Write(Byte[]Buffer,0,EncodedSizeeofMp3)并且它在给出任何异常之前成功地写入了它

流不可写异常的可能原因是什么

如果您正在向NetworkStream写入,则流/套接字可能会关闭

如果您正在写入NetworkStream,它可能是用FileAccess.Read 创建的

不过,如果非要我猜测的话,听起来好像有什么东西正在关闭流——比如说,如果沿途的"作家"认为自己拥有流,那么就会过早关闭流。必须编写并使用某种忽略Close()请求的包装器Stream是很常见的(事实上,我现在有一个,因为我正在编写一些TCP代码)。

作为一个小旁白;我通常建议不要使用BinaryFormatter进行通信(远程处理除外)——最重要的是:它不会以一种非常友好的方式"版本",但在大多数情况下也会有点冗长。

这是我目前使用的包装器,以防它有帮助(Reset()方法欺骗重置位置,因此调用方可以读取相对位置):

class NonClosingNonSeekableStream : Stream
{
    public NonClosingNonSeekableStream(Stream tail)
    {
        if(tail == null) throw new ArgumentNullException("tail");
        this.tail = tail;
    }
    private long position;
    private readonly Stream tail;
    public override bool CanRead
    {
        get { return tail.CanRead; }
    }
    public override bool CanWrite
    {
        get { return tail.CanWrite; }
    }
    public override bool CanSeek
    {
        get { return false; }
    }
    public override bool CanTimeout
    {
        get { return false; }
    }
    public override long Position
    {
        get { return position; }
        set { throw new NotSupportedException(); }
    }
    public override void Flush()
    {
        tail.Flush();
    }
    public override void SetLength(long value)
    {
        throw new NotSupportedException();
    }
    public override long Seek(long offset, SeekOrigin origin)
    {
        throw new NotSupportedException();
    }
    public override long Length
    {
        get { throw new NotSupportedException(); }
    }
    public override int Read(byte[] buffer, int offset, int count)
    {
        int read = tail.Read(buffer, offset, count);
        if (read > 0) position += read;
        return read;
    }
    public override void Write(byte[] buffer, int offset, int count)
    {
        tail.Write(buffer, offset, count);
        if (count > 0) position += count;
    }
    public override int ReadByte()
    {
        int result = tail.ReadByte();
        if (result >= 0) position++;
        return result;
    }
    public override void WriteByte(byte value)
    {
        tail.WriteByte(value);
        position++;
    }
    public void Reset()
    {
        position = 0;
    }
}