【问题标题】:DataContractSerializer serialzing the same object more than once per requestDataContractSerializer 每个请求多次序列化同一个对象
【发布时间】:2009-04-26 13:36:19
【问题描述】:

我正在编写将由 Silverlight 应用程序使用的 WCF 应用程序。我已经完成了大部分的设计工作,现在我正在做实现,这让我想出了这个问题。

这是我的应用程序中存在的一个示例:

[DataContract]
class Person
{
    [DataMember]
    private Towel mostRecentlyUsedTowel;

    [DataMember]
    private Gym gym; //the gym that this person attends

    ...
}

[DataContract]
class Gym
{
    [DataMember]
    private List<Towel> towels; //all the towels this gym owns

    ...
}

这就是我的意思:在我的应用程序中 mostRecentlyUsedTowel 将指向该人健身房的毛巾列表中的某些内容。我的一些请求会序列化一个 Person 对象。

DataContractSerializer 是否足够聪明,可以注意到它被要求序列化完全相同的对象实例两次?如果有,它是如何处理的?

如果它只是将同一个实例序列化两次,我应该如何处理这个问题,这样我就不会通过链接发送不必要的数据?

【问题讨论】:

    标签: wcf datacontractserializer


    【解决方案1】:

    以下代码:

    [TestMethod]
    public void CanSerializePerson()
    {
        var towel1 = new Towel() { Id = 1 };
        var towel2 = new Towel() { Id = 2 };
        var towel3 = new Towel() { Id = 3 };
        var gym = new Gym();
        gym.towels.Add(towel1);
        gym.towels.Add(towel2);
        gym.towels.Add(towel3);
    
        var person = new Person()
        {
          recentlyUsedTowel = towel1,
          gym = gym
        };
    
        var sb = new StringBuilder();
        using (var writer = XmlWriter.Create(sb))
        {
            var ser = new DataContractSerializer(typeof (Person));
            ser.WriteObject(writer, person);
        }
    
        throw new Exception(sb.ToString());
    }
    
    public class Person
    {
        public Towel recentlyUsedTowel { get; set; }
        public Gym gym { get; set; }
    }
    
    public class Gym
    {
        public Gym()
        {
            towels = new List<Towel>();
        }
    
        public List<Towel> towels { get; set; }
    }
    
    
    public class Towel
    {
        public int Id { get; set; }
    }
    

    将评估为:

    <?xml version="1.0" encoding="utf-16"?>
    <Person xmlns:i="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://tempuri.org">
      <gym>
        <towels>
          <Towel><Id>1</Id></Towel>
          <Towel><Id>2</Id></Towel>
          <Towel><Id>3</Id></Towel>
        </towels>
      </gym>
      <recentlyUsedTowel><Id>1</Id></recentlyUsedTowel>
    </Person>
    

    如果您将 IsReference 属性添加到 Towel 类的 DataContract 属性,如下所示:

    [DataContract(IsReference=true)]
    public class Towel
    {
        // you have to specify a [DataMember] in this because you are 
        // explicitly adding DataContract
        [DataMember]
        public int Id { get; set; }
    }
    

    你会得到这样的输出:

    <?xml version="1.0" encoding="utf-16"?>
    <Person xmlns:i="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://tempuri.org">
      <gym>
        <towels>
          <Towel z:Id="i1" xmlns:z="http://schemas.microsoft.com/2003/10/Serialization/">
            <Id>1</Id>
          </Towel>
          <Towel z:Id="i2" xmlns:z="http://schemas.microsoft.com/2003/10/Serialization/">
            <Id>2</Id>
          </Towel>
          <Towel z:Id="i3" xmlns:z="http://schemas.microsoft.com/2003/10/Serialization/">
            <Id>3</Id>
          </Towel>
        </towels>
      </gym>
      <recentlyUsedTowel z:Ref="i1" xmlns:z="http://schemas.microsoft.com/2003/10/Serialization/" />
    </Person>
    

    希望对您有所帮助。

    【讨论】:

    • 这正是我想要的。非常感谢。
    猜你喜欢
    • 2013-02-05
    • 2015-01-28
    • 2013-12-10
    • 2023-01-29
    • 2016-03-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-10-10
    相关资源
    最近更新 更多