2015-11-03 73 views
1

我試圖使用序列化的protobuf網的一些數據。在序列化期間,我收到一個錯誤,指出沒有爲Point3D類型定義的序列化。我發現了一個像這樣的問題,但仍然無法執行並解決它。鏈接如下: - No serializer defined for type: System.Drawing.Color類型定義沒有串行:System.Windows.Media.Media3D.Point3D

[ProtoContract] 
public class ReturnPanelData 
{ 
    [ProtoMember(1)] 
    public Point3D PlacedPoint3D { get; set; } 
    [ProtoMember(2)] 
    public double PlacementAngle { get; set; } 
    [ProtoMember(3)] 
    public string PanelName { get; set; } 
} 
[ProtoContract] 
public class ReturnDataType 
{ 
    [ProtoMember(1)] 
    public List<ReturnPanelData> ReturnList { get; set; } 
    [ProtoMember(2)] 
    public double RemainderArea { get; set; } 
    [ProtoMember(3)] 
    public int Height { get; set; } 
    [ProtoMember(4)] 
    public int Width { get; set; } 
    [ProtoMember(5)] 
    public Point3D BasePoint3D { get; set; } 
} 
class Program 
{ 
    private static HashSet<ReturnDataType> _processedList = new HashSet<ReturnDataType>(); 
    static void Main(string[] args) 
    { 
     using (var file = File.Create(@"D:\SavedPCInfo2.bin")) 
     { 
      Serializer.Serialize(file, _processedList); 
     } 
     Console.WriteLine("Done"); 
    } 
} 

我在JSON序列化/反序列化begineer。如何解決這個問題?

如果無法序列​​化三維點用的Protobuf網,有什麼其他的選擇序列化/反序列化一個非常大名單(具有約30萬項)?

+0

爲什麼不Newtonsoft.Json? – Camo

+0

@Rinecamo:在選擇序列化技術之前,我搜索了一些文章,發現要序列化/反序列化大列表,使用Protobuf Net是一個更好的選擇。 http://stackoverflow.com/questions/26368550/efficient-way-of-storing-and-retrieving-large-json-100-mb-from-a-file-using –

回答

1

首先,protobuf-net不是JSON串行器。它的序列化格式爲"Protocol Buffers" - Google用於其大部分數據通信的二進制序列化格式。

話雖這麼說,有幾種解決方案序列化類型,使用protobuf網,不能用ProtoContract屬性來裝飾:

  1. 當一些其他類型的包含,使用代理或「墊片」屬性如圖所示here,OR
  2. 使用替代如圖所示here,OR
  3. 在運行系統中教導RuntimeTypeModel所有序列化字段的類型的&性質的部分中所述here沒有屬性的序列化

對於第二種情況,由於Point3D完全由它的X,Y,Z座標定義的,它很容易引入序列化代理:

[ProtoContract] 
struct Point3DSurrogate 
{ 
    public Point3DSurrogate(double x, double y, double z) : this() 
    { 
     this.X = x; 
     this.Y = y; 
     this.Z = z; 
    } 

    [ProtoMember(1)] 
    public double X { get; set; } 
    [ProtoMember(2)] 
    public double Y { get; set; } 
    [ProtoMember(3)] 
    public double Z { get; set; } 

    public static implicit operator Point3D(Point3DSurrogate surrogate) 
    { 
     return new Point3D(surrogate.X, surrogate.Y, surrogate.Z); 
    } 

    public static implicit operator Point3DSurrogate(Point3D point) 
    { 
     return new Point3DSurrogate(point.X, point.Y, point.Z); 
    } 
} 

然後用protobuf網只是其註冊一旦啓動時就像這樣:

ProtoBuf.Meta.RuntimeTypeModel.Default.Add(typeof(Point3D), false).SetSurrogate(typeof(Point3DSurrogate)); 

另外,選項3,在啓動時你可以定義一個合同Point3D像這樣:

ProtoBuf.Meta.RuntimeTypeModel.Default.Add(typeof(Point3D), true); 
ProtoBuf.Meta.RuntimeTypeModel.Default[typeof(Point3D)].Add(1, "X").Add(2, "Y").Add(3, "Z"); 

(在我看來,代孕是,儘管需要更多的代碼更清晰;完全在運行時定義協議似乎太過分)

我不建議選項1,因爲您需要爲所有使用Point3D的類添加代理屬性。

+0

謝謝主席先生。你解釋它的方式非常有趣。 –

相關問題