How to serialize an object into an array of bytes (Portable Class Library)
I have an object that I want to serialize into byte[]
in order to save it or move it around. Let's assume it's:
public class Message
{
public MessageType MessageType { get; set; }
public byte[] Body { get; set; }
}
public enum MessageType : byte
{
Type1 = 1,
Type2 = 2,
}
My code is a .Net 4.5, Windows 8.1 and Windows Phone 8.1 PCL (Portable Class Library), and all the libraries, examples, and answers I came across don't work with PCL, mostly because of their use of BinaryFormatter
, which is not available in PCL.
So, how to go about it?
With a class that simple just write your own serializer using BinaryWriter and BinaryReader (Both useable in PCL projects)
public class Message
{
public MessageType MessageType { get; set; }
public byte[] Body { get; set; }
public byte[] Serialize()
{
//Data will be serialized in the format
// - MessageType (1 byte)
// - BodyLength (4 bytes)
// - Body (x Bytes)
//We allocate a fixed buffer as we know the size already.
var buffer = new byte[Body.Length + 5];
using(var ms = new MemoryStream(buffer)
{
Serialize(ms);
}
//Return our buffer.
return buffer
}
//Just in case you have a stream instead of a byte[]
public void Serialize(Stream stream)
{
using(var writer = new BinaryWriter(stream, Encoding.UTF8, true))
{
writer.Write((byte)this.MessageType);
writer.Write(Body.Length);
writer.Write(Body);
}
}
public static Message Deserialize(byte[] data)
{
using(var ms = new MemoryStream(data))
{
return Message.Deserialize(ms);
}
}
//Just in case you have a stream instead of a byte[]
public static Message Deserialize(Stream data)
{
var message = new Message();
//Use the default text encoding (does not matter for us) and leave the stream open.
using(var reader = new BinaryReader(data, Encoding.UTF8, true))
{
//We do the same order of operations.
message.MessageType = (MessageType)reader.ReadByte();
var bodyLength = reader.ReadInt32();
message.Body = reader.ReadBytes(bodyLength);
}
return message;
}
}
Here is a simplified version if you are never going to use Streams for deserializing.
public byte[] Serialize()
{
//Data will be serialized in the format
// - MessageType (1 byte)
// - Body (x Bytes)
//We allocate a fixed buffer as we know the size already.
var data = new byte[Body.Length + 1];
data[0] = (byte)this.MessageType;
//We copy the data from Body in to data starting at index 1 in data.
Array.Copy(Body, 0, data, 1, Body.Length);
return data;
}
public static Message Deserialize(byte[] data)
{
var message = new Message();
//We do the same order of operations.
message.MessageType = (MessageType)data[0];
//Create a new array and copy the body data in to it.
var body = new byte[data.Length - 1];
Array.Copy(data, 1, body, 0, data.Length - 1);
//Assign the body array to the property.
message.Body = body;
return message;
}
}
链接地址: http://www.djcxy.com/p/68860.html
上一篇: 在C#中的可移植类库中访问串行端口
下一篇: 如何将对象序列化为字节数组(可移植类库)