我得到一個異常,試圖序列化對象圖(不是很深)。它有意義的部分是這樣的:protobuf-net:檢測到可能的遞歸
[ERROR]致命未處理的異常:ProtoBuf.ProtoException:可能 遞歸d etected(偏移量:5級(S)):紅色在 ProtoBuf.ProtoWriter.CheckRecursionStackAndPush(對象)< 0x00127>在 ProtoBuf.ProtoWriter.StartSubItem(對象,ProtoBuf.ProtoWriter,布爾) < 0x0002f>
該圖表示的文件/目錄結構和我的模型(簡化的)是這樣的:
[ProtoContract]
[ProtoInclude(100, typeof(PackageDirectory))]
[ProtoInclude(200, typeof(PackageFile))]
public abstract class PackageMember
{
[ProtoMember(1)]
public virtual string Name { get; protected set; }
[ProtoMember(2, AsReference=true)]
public PackageDirectory ParentDirectory { get; protected set; }
}
[ProtoContract]
public class PackageDirectory : PackageMember
{
[ProtoMember(3)]
private Dictionary<string, PackageMember> _children;
public PackageDirectory()
{
_children = new Dictionary<string, PackageMember>();
}
public PackageDirectory (string name, PackageDirectory parentDirectory)
: this()
{
this.ParentDirectory = parentDirectory;
this.Name = name;
}
public void Add (PackageMember member)
{
_children.Add(member.Name, member);
}
}
[ProtoContract]
public class PackageFile : PackageMember
{
private Stream _file;
private BinaryReader _reader;
private PackageFile()
{}
public PackageFile (string name, int offset, int length, PackageDirectory directory, Stream file)
{
this.Name = name;
this.Length = length;
this.Offset = offset;
this.ParentDirectory = directory;
_file = file;
_reader = new BinaryReader(_file);
}
[OnDeserialized]
protected virtual void OnDeserialized(SerializationContext context)
{
var deserializationContext = context.Context as DeserializationContext;
if (deserializationContext != null)
{
_file = deserializationContext.FileStream;
_reader = new BinaryReader(_file);
}
}
[ProtoMember(3)]
public int Offset { get; private set; }
[ProtoMember(4)]
public int Length { get; private set; }
}
該樹的深度接近10-15級,小於ProtoBuf.ProtoWriter.RecursionCheckDepth
值(25)。 (所以也許這是一個錯誤?) 版本的protobuf網使用是一個編譯從中繼v2(轉491)。
其實,我解決了它與修改protobuf網絡代碼。我將ProtoBuf.ProtoWriter.RecursionCheckDepth
的值更改爲100,一切似乎都沒問題。
問題是如果有任何「真正」的方式來序列化這種類型的圖,而不修改protobuf代碼?這樣的行爲是正確的還是錯誤?
我的平臺是單-2.10-8在Windows 7專業版64位
附:我還發現,如果我deserizlie與thw下面的代碼,我應該有PackageDirectory無參數構造函數公開。
var value = new PackageDirectory();
RuntimeTypeModel.Default.Deserialize(ms, value, typeof(PackageDirectory), new SerializationContext {
Context = new DeserializationContext {
FileStream = _file,
}});
這是另一個話題,但它提供的代碼很好地說明。我認爲在這種情況下應該允許聲明私有構造函數,因爲現在行爲與Serializer.Deserialize(...)的行爲不同。
該構造函數的問題聽起來很奇怪和意外 - 再次,將需要repro;這個運行的平臺是什麼?正規的.NET?要麼...?(由於平臺的限制,SL和CF在這裏有一些細微的差別) – 2012-04-09 09:03:22
@MarcGravell,對不完整的信息抱歉,我忘了指定我的平臺。它是單聲道的。我會編輯一個問題。 – ILya 2012-04-09 15:51:09
單聲道...? Linux呢? iOS版?另外:您使用的是哪個**確切的**版本號? – 2012-04-09 17:23:23