序列化图表时出现异常
我仍在使用新发布的 protobuf-net 版本,但遇到了一个我不明白的问题。
让我们考虑下面的代码片段:
[ProtoContract]
class Node
{
public Node()
{
Children = new List<Node>();
}
[ProtoMember(1, IsRequired = true)]
public int Data { get; set; }
[ProtoMember(2, IsRequired = true, AsReference = true)]
public List<Node> Children { get; set; }
public void AddChild(Node child)
{
Children.Add(child);
}
}
static void Main()
{
Node n = new Node {Data = 0}, root = n;
for (int i=1; i<15; i++)
{
Node child = new Node {Data = i};
n.AddChild(child);
n = child;
}
Node clone = Serializer.DeepClone(root);
}
它抛出 ProtoException
类型的异常,并显示消息“检测到可能的递归...”
有趣的是,如果我删除属性 AsReference
> 在 Children
属性上它没有!不幸的是,上面的行只是为了说明问题而编写的,我需要这个属性来实现我正在使用的实际结构。
所以我的问题是...这是一个已知问题吗?是否有任何补丁计划很快修复它?或者有人知道任何解决方法吗?
谢谢
I'm still playing with the newly released version of protobuf-net and I'm facing an issue I don't understand.
let's consider the piece of code below:
[ProtoContract]
class Node
{
public Node()
{
Children = new List<Node>();
}
[ProtoMember(1, IsRequired = true)]
public int Data { get; set; }
[ProtoMember(2, IsRequired = true, AsReference = true)]
public List<Node> Children { get; set; }
public void AddChild(Node child)
{
Children.Add(child);
}
}
static void Main()
{
Node n = new Node {Data = 0}, root = n;
for (int i=1; i<15; i++)
{
Node child = new Node {Data = i};
n.AddChild(child);
n = child;
}
Node clone = Serializer.DeepClone(root);
}
It throws a exception of type ProtoException
with the message "Possible recursion detected..."
The funny thing is that if I remove the attribute AsReference
on the Children
property it doesn't! Unfortunately, the lines above are just written to illustrate the problem and I need this attribute for the real structure I'm using.
So my question is... is it a known problem and is there any patch planned to fix it very soon? Or does anyone know any workaround?
Thanks
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
这只是一个错误(感谢您如此彻底地练习测试版!) - 在动态/引用处理中,它对对象进行了双重计数(一次作为填充程序包装器的一部分,它欺骗了魔法,一次为对象本身)。
为了提高效率,递归检测仅在超过特定深度时才全面启动。您的代码超出了这个深度,导致重复计数被视为递归。我已经在代码中修复了这个问题。上面的代码在本地传递,并将在下一滴中。
This is simply a bug (thank you for exercising the beta so thoroughly!) - in the dynamic/reference handling it was double-counting the object (once as part of the shim wrapper it spoofs to do the magic, and once for the object itself).
For efficiency, the recursion detection only kicks into full gear beyond a specific depth. Your code tripped this depth, causing the double-counting to be seen as recursion. I have fixed this in the code. The code above passes locally, and will be in the next drop.