Как правильно перевести в массив байт COM-объект и/или объекты, к классам которым нельзя получить доступ и поставить им атрибут Serializable
(например, из сторонних библиотек)?
Например надо сериализовать следующие классы:
class SampleClass1
{
public int SampleField1 { get; set; }
public string SampleField2 { get; set; }
public SampleClass2 SampleField3 { get; set; }
}
class SampleClass2
{
public int SampleField1 { get; set; }
public string SampleField2 { get; set; }
}
Вариант 1:
class Serializer1
{
[Serializable]
private class SampleClassProxy : ISerializable
{
public readonly SampleClass1 Obj;
public SampleClassProxy()
{
Obj = new SampleClass1();
}
public SampleClassProxy(SampleClass1 obj)
{
Obj = obj;
}
public SampleClassProxy(SerializationInfo info, StreamingContext context)
{
Obj = new SampleClass1() {
SampleField1 = info.GetInt32("SampleField1"),
SampleField2 = info.GetString("SampleField2"),
SampleField3 = new SampleClass2() {
SampleField1 = info.GetInt32("SampleField3.SampleField1"),
SampleField2 = info.GetString("SampleField3.SampleField2")
}
};
}
public void GetObjectData(SerializationInfo info, StreamingContext context)
{
info.AddValue("SampleField1", Obj.SampleField1);
info.AddValue("SampleField2", Obj.SampleField2);
info.AddValue("SampleField3.SampleField1", Obj.SampleField3.SampleField1);
info.AddValue("SampleField3.SampleField2", Obj.SampleField3.SampleField2);
}
}
public static void DoWork()
{
var obj = new SampleClass1() {
SampleField1 = 1,
SampleField2 = "2",
SampleField3 = new SampleClass2() {
SampleField1 = 3,
SampleField2 = "4"
}
};
var proxy = new SampleClassProxy(obj);
var formatter = new BinaryFormatter();
var bytes = Serialize(formatter, proxy);
var proxy2 = Deserialize(formatter, bytes);
var obj2 = proxy2.Obj;
}
private static byte[] Serialize(IFormatter formatter, SampleClassProxy obj)
{
using (var stream = new MemoryStream()) {
formatter.Serialize(stream, obj);
return stream.ToArray();
}
}
private static SampleClassProxy Deserialize(IFormatter formatter, byte[] bytes)
{
using (var stream = new MemoryStream(bytes)) {
return (SampleClassProxy)formatter.Deserialize(stream);
}
}
}
Вариант 2:
class Serializer2
{
private class SampleClass1Surrogate : ISerializationSurrogate
{
public void GetObjectData(object obj, SerializationInfo info, StreamingContext context)
{
var sampleClass = (SampleClass1)obj;
info.AddValue("SampleField1", sampleClass.SampleField1);
info.AddValue("SampleField2", sampleClass.SampleField2);
info.AddValue("SampleField3", sampleClass.SampleField3);
}
public object SetObjectData(object obj, SerializationInfo info, StreamingContext context, ISurrogateSelector selector)
{
var sampleClass = (SampleClass1)obj;
sampleClass.SampleField1 = info.GetInt32("SampleField1");
sampleClass.SampleField2 = info.GetString("SampleField2");
sampleClass.SampleField3 = (SampleClass2)info.GetValue("SampleField3", typeof(SampleClass2));
return sampleClass;
}
}
private class SampleClass2Surrogate : ISerializationSurrogate
{
public void GetObjectData(object obj, SerializationInfo info, StreamingContext context)
{
var sampleClass = (SampleClass2)obj;
info.AddValue("SampleField1", sampleClass.SampleField1);
info.AddValue("SampleField2", sampleClass.SampleField2);
}
public object SetObjectData(object obj, SerializationInfo info, StreamingContext context, ISurrogateSelector selector)
{
var sampleClass = (SampleClass2)obj;
sampleClass.SampleField1 = info.GetInt32("SampleField1");
sampleClass.SampleField2 = info.GetString("SampleField2");
return sampleClass;
}
}
public static void DoWork()
{
var obj = new SampleClass1() {
SampleField1 = 1,
SampleField2 = "2",
SampleField3 = new SampleClass2() {
SampleField1 = 3,
SampleField2 = "4"
}
};
IFormatter formatter = new BinaryFormatter();
var surrogateSelector = new SurrogateSelector();
surrogateSelector.AddSurrogate(typeof(SampleClass1), new StreamingContext(StreamingContextStates.All), new SampleClass1Surrogate());
surrogateSelector.AddSurrogate(typeof(SampleClass2), new StreamingContext(StreamingContextStates.All), new SampleClass2Surrogate());
formatter.SurrogateSelector = surrogateSelector;
var bytes = Serialize(formatter, obj);
var obj2 = Deserialize(formatter, bytes);
}
private static byte[] Serialize(IFormatter formatter, SampleClass1 obj)
{
using (var stream = new MemoryStream()) {
formatter.Serialize(stream, obj);
return stream.ToArray();
}
}
private static SampleClass1 Deserialize(IFormatter formatter, byte[] bytes)
{
using (var stream = new MemoryStream(bytes)) {
return (SampleClass1)formatter.Deserialize(stream);
}
}
}
Айфон мало держит заряд, разбираемся с проблемой вместе с AppLab
Перевод документов на английский язык: Важность и ключевые аспекты
Всем приветПомогите пожалуйста с Dictionary