2012-02-21 1 views
2

Я пытаюсь сериализовать модель, используя отличный Protobuf-NET. Я не могу использовать атрибуты (объекты неизвестны во время компиляции), поэтому я построил TypeModel. Моя объектная модель состоит из класса TestDataObject, этот класс обладает свойством ITestDataExtension. Абстрактный базовый класс TestDataExtensionBase реализует этот интерфейс и класс TestDataExtension (myDataObjectExtA в коде) наследует этот базовый класс.Protobuf-net создание типовой модели с интерфейсом и абстрактным базовым классом

Мой TypeModel строится так:

 System.IO.MemoryStream tmpMemoryStream = new System.IO.MemoryStream(); 
     RuntimeTypeModel model = TypeModel.Create(); 
     MetaType basetype = model.Add(typeof(TestDataObject), true); 
     MetaType interfaceType = model.Add(typeof(ITestDataExtension), true); 
     //MetaType extBaseType = interfaceType.AddSubType(100, typeof(TestDataExtensionBase)); 
     MetaType extType = interfaceType.AddSubType(200, myDataObjectExtA.GetType()); 
     model.Add(typeof(TestDataExtensionBase), true); 
     model.Add(myDataObjectA.Ext.GetType(), true); 
     model.CompileInPlace(); 
     model.Serialize(tmpMemoryStream, myDataObjectA); 
     byte[] tmpDat = tmpMemoryStream.ToArray(); 

Если я запускаю следующие свойства базового класса не сериализации, и мне нужно, чтобы они были упорядочены.
По моему мнению, я должен был добавить подтип для TestDataExtensionBase как это:

 MetaType extBaseType = interfaceType.AddSubType(100, typeof(TestDataExtensionBase)); 
     MetaType extType = extBaseType.AddSubType(200, myDataObjectExtA.GetType()); 

Но это приводит к: Неожиданное подтипа: TestDataExtension. Кто-нибудь знает, что я делаю неправильно? Любая помощь будет оценена по достоинству.

ответ

4

2 выпуска:

  • поддержка интерфейса только в настоящее время, предусмотренные членов, а не корневые объекты (из-за проблем множественного наследования интерфейса); Самый простой способ обойти это использовать объект-оболочку с интерфейсом членом
  • необходимо определить подтипы в модели

Я думаю следующего делает то, что вы описали ...?

using System; 
using ProtoBuf.Meta; 

interface ITest 
{ 
    int X { get; set; } 
} 
abstract class TestBase : ITest 
{ 
    public int X { get; set; } // from interface 
    public int Y { get; set; } 
} 
class Test : TestBase 
{ 
    public int Z { get; set; } 
    public override string ToString() 
    { 
     return string.Format("{0}, {1}, {2}", X, Y, Z); 
    } 
} 
class Wrapper 
{ 
    public ITest Value { get; set; } 
} 
public class Program 
{ 
    static void Main() 
    { 
     var model = TypeModel.Create(); 
     model.Add(typeof (ITest), false).Add("X") 
       .AddSubType(10, typeof (TestBase)); 
     model.Add(typeof (TestBase), false).Add("Y") 
       .AddSubType(10, typeof (Test)); 
     model.Add(typeof (Test), false).Add("Z"); 
     model.Add(typeof (Wrapper), false).Add("Value"); 

     Wrapper obj = new Wrapper {Value = new Test() 
       {X = 123, Y = 456, Z = 789}}; 

     var clone = (Wrapper)model.DeepClone(obj); 
     Console.WriteLine(clone.Value); 
    } 
} 
+0

Как всегда, anwser, по-видимому, довольно прост, это работает как шарм. Большое спасибо за быстрый ответ. – pabes