如何让自己的Stream类支持序列化
public class SocketStream : Stream, IDisposable
{
private bool _isDispose;
private bool _isSocketClose;
private bool _isWork;
private bool _isWrite;
public IMemoryPool Pool { get; }
public IBuffer WriteBuffer { get; }
public IBuffer ReadBuffer { get; }
public Socket Socket { get; }
SocketAsyncEventArgs ReadAsyncArgs = new SocketAsyncEventArgs();
protected void Initial()
{
ReadAsyncArgs.Completed += ReadAsyncArgs_Completed;
ReadAsyncArgs.SetBuffer(ReadBuffer.Buffer, ReadBuffer.Offset, ReadBuffer.Count);
}
public void Work()
{
lock (this)
{
if (_isWork == false)
{
_isWork = true;
if (ReadBuffer.Count > 0)
{
ReadAsyncArgs.SetBuffer(ReadBuffer.Offset, ReadBuffer.Count);
if (!this.Socket.ReceiveAsync(ReadAsyncArgs))
{
throw new SocketException();
}
}
else
{
_isWork = false;
}
}
}
}
private void WriteAsyncArgs_Completed(object sender, SocketAsyncEventArgs e)
{
e.Dispose();
}
private void ReadAsyncArgs_Completed(object sender, SocketAsyncEventArgs e)
{
_isWork = false;
if (e.BytesTransferred > 0)
{
this.ReadBuffer.Offset += e.BytesTransferred;
if (ReadSleep != null)
{
ReadSleep.TrySetResult(true);
}
Work();
}
else
{
_isSocketClose = true;
}
}
public SocketStream(Socket Socket, IBuffer ReadBuffer, IBuffer WriteBuffer)
{
this.WriteBuffer = WriteBuffer;
this.ReadBuffer = ReadBuffer;
this.Socket = Socket;
this.Initial();
}
public SocketStream(Socket Socket, IMemoryPool Pool)
: this(Socket, Pool.Malloc(), Pool.Malloc())
{
}
public override bool CanRead
{
get
{
NetworkStream ms = new NetworkStream(null);
return Socket != null && Socket.Connected;
}
}
public override bool CanSeek
{
get
{
return false;
}
}
public override bool CanWrite
{
get
{
return Socket != null && Socket.Connected;
}
}
public override long Length
{
get
{
throw new NotSupportedException();
}
}
public override long Position
{
get
{
throw new NotSupportedException();
}
set
{
throw new NotSupportedException();
}
}
public override void Flush()
{
lock (this)
{
if (this.WriteBuffer.EffectiveBegin < this.WriteBuffer.Offset)
{
SocketAsyncEventArgs WriteAsyncArgs = new SocketAsyncEventArgs();
WriteAsyncArgs.Completed += WriteAsyncArgs_Completed;
WriteAsyncArgs.SetBuffer(WriteBuffer.Buffer, WriteBuffer.Offset, WriteBuffer.Count);
WriteAsyncArgs.SetBuffer(this.WriteBuffer.EffectiveBegin, this.WriteBuffer.Offset);
this.WriteBuffer.Offset = 0;
if (!this.Socket.SendAsync(WriteAsyncArgs))
{
throw new SocketException();
}
}
}
}
public override int Read(byte[] buffer, int offset, int count)
{
var task = ReadAsync(buffer, offset, count);
task.Wait();
return task.Result;
}
TaskCompletionSource<bool> ReadSleep = null;
public override async Task<int> ReadAsync(byte[] buffer, int offset, int count, CancellationToken cancellationToken)
{
if (ReadSleep != null)
{
throw new Exception("不支持多线程操作");
}
ReadSleep = new TaskCompletionSource<bool>();
while (!(this.ReadBuffer.Offset > this.ReadBuffer.EffectiveBegin))
{
await ReadSleep.Task;
}
ReadSleep = null;
int ret = this.ReadBuffer.Read(buffer, offset, count);
if (_isWork == false)
{
Work();
}
return ret;
}
public override long Seek(long offset, SeekOrigin origin)
{
throw new NotSupportedException();
}
public override void SetLength(long value)
{
throw new NotSupportedException();
}
public override void Write(byte[] buffer, int offset, int count)
{
this.WriteBuffer.Write(buffer, offset, count);
}
public override async Task WriteAsync(byte[] buffer, int offset, int count, CancellationToken cancellationToken)
{
Write(buffer, offset, count);
}
public override int ReadByte()
{
byte[] t = new byte[1];
int len = Read(t, 0, 1);
return t[0];
}
public override void WriteByte(byte value)
{
this.WriteBuffer.WriteByte(value);
}
public async Task<int> ReadSpecifiesAsync(byte[] buffer, int offset, int count)
{
int end = offset + count;
while (offset < end )
{
offset += await this.ReadAsync(buffer, offset, end - offset);
}
if(count - (end - offset) != 0)
{
throw new Exception("Socket 无法读取对应数据或者已经取消");
}
return count;
}
public async Task<byte[]> ReadSpecifiesAsync(int count)
{
byte[] date = new byte[16];
int len = await ReadSpecifiesAsync(date, 0, date.Length);
if (len < date.Length)
{
throw new SocketException();
}
return date;
}
public async Task<T> ReadVar<T>()
{
if (typeof(T) == typeof(Int16))
{
return (T)(object)BitConverter.ToInt16(await ReadSpecifiesAsync(16), 0);
}
else if (typeof(T) == typeof(Int32))
{
return (T)(object)BitConverter.ToInt32(await ReadSpecifiesAsync(32), 0);
}
else if (typeof(T) == typeof(Int64))
{
return (T)(object)BitConverter.ToInt64(await ReadSpecifiesAsync(64), 0);
}
else if (typeof(T) == typeof(double))
{
return (T)(object)BitConverter.ToDouble(await ReadSpecifiesAsync(64), 0);
}
else if (typeof(T) == typeof(short))
{
return (T)(object)BitConverter.ToSingle(await ReadSpecifiesAsync(32), 0);
}
else if (typeof(T) == typeof(bool))
{
return (T)(object)BitConverter.ToBoolean(await ReadSpecifiesAsync(1), 0);
}
else if (typeof(T) == typeof(char))
{
return (T)(object)BitConverter.ToChar(await ReadSpecifiesAsync(1), 0);
}
else if (typeof(T) == typeof(UInt16))
{
return (T)(object)BitConverter.ToUInt16(await ReadSpecifiesAsync(16), 0);
}
else if (typeof(T) == typeof(UInt32))
{
return (T)(object)BitConverter.ToInt32(await ReadSpecifiesAsync(16), 0);
}
else if (typeof(T) == typeof(UInt64))
{
return (T)(object)BitConverter.ToInt64(await ReadSpecifiesAsync(16), 0);
}
else
{
return (T)(object)0;
}
}
protected override void Dispose(bool disposing)
{
lock (this)
{
if (_isDispose == false)
{
_isDispose = true;
base.Dispose(disposing);
if (!disposing)
{
if (Pool != null)
{
Pool.Free(this.WriteBuffer);
Pool.Free(this.ReadBuffer);
}
if (ReadAsyncArgs != null)
{
ReadAsyncArgs.SetBuffer(null, 0, 0);
ReadAsyncArgs.Completed -= this.ReadAsyncArgs_Completed;
ReadAsyncArgs.Dispose();
ReadAsyncArgs = null;
}
}
}
else
{
throw new ObjectDisposedException(this.GetType().ToString());
}
}
}
}
...全文
相关推荐
C#实现的json序列化和反序列化代码实例
这个类提供了序列化和反序列化.NET对象到JSON字符串的能力。
Unity 中使用Protobuf进行序列化和反序列化的Demo
然后,使用protobuf-net的工具(如`protogen.exe`)将.proto文件编译为C#类。这个编译后的类可以被Unity中的脚本直接使用。
NET 中的对象序列化
序列化在许多场景下都非常有用,比如在跨进程通信、网络传输、数据备份和恢复等方面。要实现.NET中的对象序列化,首先需要让类支持序列化。最常用的方式是在类定义上添加`[Serializable]`属性。
C#中实现Json序列化与反序列化的几种方式
`不支持所有JSON特性,比如日期格式可能会有所不同。
C# XML和类之间的转化,序列化
同样使用XmlSerializer类,但这次我们需要调用Deserialize方法,并传入包含XML数据的TextReader或Stream对象。


