使用 WCF 反序列化 XML 字符串

Posted

技术标签:

【中文标题】使用 WCF 反序列化 XML 字符串【英文标题】:Deserialize an XML string with WCF 【发布时间】:2021-06-07 01:49:57 【问题描述】:

我在将 XML 字符串反序列化为 C# 对象时遇到问题。问题是我的结果将永远为空。这是我存储在字符串变量中的 XML 字符串。

<objects>
  <object>
    <dateadded>1614924419</dateadded>
    <id>CF7E7B22-1D3A-4CFE-91F9-F8C5C2DB4069</id>
    <name>NorthernLights</name>
    <parentid>ED98C97F-A202-48ED-AEEA-34362508A30B</parentid>
    <type>file</type>
  </object>
  <object>
    <dateadded>1614924419</dateadded>
    <id>CF7E7B22-1D3A-4CFE-91F9-F8C5C2DB4070</id>
    <name>Northern</name>
    <parentid>ED98C97F-A202-48ED-AEEA-34362508A30C</parentid>
    <type>file</type>
  </object>
</objects>

这些是我创建的代表 XML 文档的类。 我想那里有问题。有人可以帮我解决这个问题吗?

这是objects标签的类:

namespace DataContractSample.DataContract.Model

    using System.Collections.Generic;
    using System.Runtime.Serialization;

    [DataContract(Name = "objects", Namespace = "", IsReference = false)]
    [KnownType(typeof(IList<Image>))]

    public class Images
    
        [DataMember(Name = "object", EmitDefaultValue = false, IsRequired = true)]
        public IList<Image> ImageList;
    

这是object标签的类:

namespace DataContractSample.DataContract.Model

    using System;
    using System.Runtime.Serialization;

    [DataContract(Name = "object", Namespace = "")]
    public class Image
    
        [DataMember(Name = "Id")]
        public Guid id  get; set; 

        [DataMember(Name="parentid")]
        public Guid ParentId  get; set; 

        [DataMember(Name="name")]
        public string Name  get; set; 
        
        [DataMember(Name = "type")]
        public string Type  get; set; 

        [DataMember(Name = "dateadded")]
        public string DateAdded  get; set; 
    

谢谢!

【问题讨论】:

你能和我们分享一下你如何调用反序列化方法吗? var dataContractSerializerUtility = new DataContractSerializerUtility(); var sortabledataContractSerializer = new DataContractSortableSerializerUtility(dataContractSerializerUtility);图片 imageList = sortabledataContractSerializer.DeSerializer(XMLString); 您是否尝试过使用List&lt;Image&gt; 而不是IList&lt;Image&gt;KnownTypes 属性对我来说也很奇怪。它应该在继承的情况下使用,但这里我们没有。 是的,我尝试同时使用 List 和 IList 并且结果是一样的。我尝试按照您的建议删除 KnowTypes 属性,但它也不适用于该更改。 在下面的帖子中,我详细介绍了这个问题并展示了两种可能的解决方案。它们都不依赖于KnownTypes 属性。 【参考方案1】:

您的方法的问题是您希望同时将 &lt;objects&gt; 反序列化为 classproperty。这行不通。在这里,我提出了两种不同的方法来解决这个问题。

选项 A

如果您在&lt;objects&gt; 周围有一个外部节点:

<?xml version="1.0" encoding="utf-8" ?>
<top>
  <objects>
    <object>
      <dateadded>1614924419</dateadded>
      <id>CF7E7B22-1D3A-4CFE-91F9-F8C5C2DB4069</id>
      <name>NorthernLights</name>
      <parentid>ED98C97F-A202-48ED-AEEA-34362508A30B</parentid>
      <type>file</type>
    </object>
    <object>
      <dateadded>1614924419</dateadded>
      <id>CF7E7B22-1D3A-4CFE-91F9-F8C5C2DB4070</id>
      <name>Northern</name>
      <parentid>ED98C97F-A202-48ED-AEEA-34362508A30C</parentid>
      <type>file</type>
    </object>
  </objects>
</top>

使用此修改后的***实体:

[DataContract(Name = "top", Namespace = "", IsReference = false)]
public class Images

    [DataMember(Name = "objects", EmitDefaultValue = false, IsRequired = true)]
    public List<Image> ImageList;

然后反序列化就像一个魅力:

using var file = File.OpenRead("sample.xml");
using var reader = new XmlTextReader(file); 
var serializer = new DataContractSerializer(typeof(Images));
var data = (Images)serializer.ReadObject(reader);

Console.WriteLine(data.ImageList.Count); // Will print 2

选项 B

如果&lt;objects&gt; 周围没有外部节点,则可以使用CollectionDataContract

[CollectionDataContract(Name = "objects", Namespace = "")]
public class Images: List<Image>



它也会起作用:

using var file = File.OpenRead("sample.xml");
using var reader = new XmlTextReader(file); 
var serializer = new DataContractSerializer(typeof(Images));
var data = (Images)serializer.ReadObject(reader);

Console.WriteLine(data.Count); // Will print 2

【讨论】:

你是上帝彼得!你已经解决了我的问题:-) 一切正常!你的承诺和帮助应该得到全世界的感谢!

以上是关于使用 WCF 反序列化 XML 字符串的主要内容,如果未能解决你的问题,请参考以下文章

WCF -Rest- DataContract:反序列化 XML 包装的响应

在 C# 中为 WCF 服务反序列化简单的 XML 数组对象

如何序列化/反序列化 C# WCF DataContract 到 XML

C# Restful WCF 服务。无法在帖子正文中反序列化 XML

如何使用 DataContractSerializer 从文件中反序列化 WCF 肥皂响应消息?

在反序列化时使用动态和强制执行 WCF 合同