序列化期间出现 StackOverFlowException

发布于 2024-10-17 11:49:36 字数 928 浏览 8 评论 0原文

我尝试序列化一个自定义类型,该类型在其他成员中保存字典。与字典的键和值关联的类型是实现的接口。

字典看起来像

 Dictionary<ITypeA, ITypeA> 

TypeA implements ITypeA, 
SubTypeOfA inherits from TypeA
SubTypeOfB inherits from SubTypeOfA

伪代码,如下所示:

            List<Type> knownTypes = new List<Type>() { 
                typeof(TypeA), 
                typeof(SubTypeOfA),
                typeof(SubTypeOfB)
            };

DataContractSerializer serializer =
                new DataContractSerializer(typeof(DataHolder), knownTypes);

            using (FileStream fs = new FileStream(completeFilePath, FileMode.Create))
            {
                serializer.WriteObject(fs, templateData);
                success = true;
            }

当调用 WriteObject() 时,我收到 StackOverflowException,我不知道是什么导致了这种情况发生。

层次结构中的所有类都用 [DataContract] 装饰,要序列化的成员用 [DataMember] 装饰。

任何帮助将不胜感激。

I trying to serialize a custom type which holds a dictionary among other members. The types associated with key and value of the dictionary are interfaces which are implemented.

The dictionary looks like

 Dictionary<ITypeA, ITypeA> 

TypeA implements ITypeA, 
SubTypeOfA inherits from TypeA
SubTypeOfB inherits from SubTypeOfA

pseudo code looks something like this:

            List<Type> knownTypes = new List<Type>() { 
                typeof(TypeA), 
                typeof(SubTypeOfA),
                typeof(SubTypeOfB)
            };

DataContractSerializer serializer =
                new DataContractSerializer(typeof(DataHolder), knownTypes);

            using (FileStream fs = new FileStream(completeFilePath, FileMode.Create))
            {
                serializer.WriteObject(fs, templateData);
                success = true;
            }

I get a StackOverflowException when WriteObject() is getting called, am clueless on what is causing that to happen.

All the classes in the hierarchy are decorated with [DataContract] and the members to be serialized are decoreated with [DataMember].

Any help would be appreciated.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

爱的十字路口 2024-10-24 11:49:36

如果图中有一个循环,但不知何故检测为对象标识失败,我可能会期望类似的结果。通过循环,我的意思是:

using System.Runtime.Serialization;
[DataContract] class Foo {
    public Foo() { Bar = this; }
    [DataMember] public Foo Bar { get; set; }
    static void Main() {
        new DataContractSerializer(typeof(Foo)).WriteObject(
            System.IO.Stream.Null, new Foo());
    }
}

它会抛出错误:

“Foo”类型的对象图包含循环,如果禁用引用跟踪,则无法序列化。

这是因为它试图遍历树(而不是图),并注意到重复(相同的对象引用),然后停止。然而,通过测试上述内容(并查看何时调用 get),看起来 DCS 实际上是通过发现疼痛来做到这一点的 - 中止之前的深度非常高。

在本地,我在 Bar 消失之前收到了 528 次调用。如果堆栈中已经有复杂的代码上面,那么它肯定会导致堆栈溢出。

I might expect something like this if you have a cycle in the graph, but which is somehow not detected as an object identity failure. By cyclic, I mean:

using System.Runtime.Serialization;
[DataContract] class Foo {
    public Foo() { Bar = this; }
    [DataMember] public Foo Bar { get; set; }
    static void Main() {
        new DataContractSerializer(typeof(Foo)).WriteObject(
            System.IO.Stream.Null, new Foo());
    }
}

which throws the error:

Object graph for type 'Foo' contains cycles and cannot be serialized if reference tracking is disabled.

This is because it is trying to walk the tree (not a graph), and noticing a repeat (identical object reference), and stopping. However, by testing the above (and seeing when the get is called), it looks like DCS actually does this by spotting pain - the depth before it aborts is very high.

Locally, I get 528 calls to Bar before it dies. If you already have complex code above this in the stack, it could account for a stack overflow, for sure.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文