gpt4 book ai didi

c# - 反序列化没有命名空间但在需要命名空间的类中的 XML

转载 作者:太空狗 更新时间:2023-10-29 17:41:07 25 4
gpt4 key购买 nike

Duplicate:
Omitting all xml namespaces when serializing an object? Not the same.. I want in the other way: Deserialize!


我有一个如下所示的 C# 类:

[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.42")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(Namespace = "http://www.portalfiscal.inf.br/nfe")]
[System.Xml.Serialization.XmlRootAttribute("NFe", Namespace = "http://www.portalfiscal.inf.br/nfe", IsNullable = false)]
public partial class TNFe
{

private TNFeInfNFe infNFeField;

private SignatureType signatureField;

/// <remarks/>
public TNFeInfNFe infNFe
{ ...

我使用此类根据用户请求序列化/反序列化 XML 文件。但是我遇到了一个问题:这个软件的新版本添加了 namespace 定义。XML 仍然相同,只是添加了 namespace 定义。

例如,上一个版本...

<?xml version="1.0" encoding="utf-8" ?>
<NFe>
<infNFe version="1.10">
...

和新版本...

<?xml version="1.0" encoding="utf-8" ?> 
<NFe xmlns="http://www.portalfiscal.inf.br/nfe">
<infNFe version="2.10">
...

我需要加载带有和不带有这些命名空间的 XML 文件。我有很多嵌套类,每个类都有自己的命名空间定义。

我想对两种 XML 使用相同的类,无论是否使用命名空间。

我尝试创建一个 XmlTextReader 并覆盖 NamespaceURI 方法,但我仍然收到没有太多信息的异常。我认为 .NET 引擎试图针对 XML 强制类命名空间定义。

最佳答案

我在代理类方面遇到过类似的挑战。由于我不会深入的原因,我需要在 Web 服务器上使用 XmlSerializer 手动序列化类,并在客户端反序列化。我无法在网上找到一个优雅的解决方案,所以我只是通过在 Visual Studio 中自动生成 XmlTypeAttribute 后手动从代理类中删除它来避免这个问题。

我一直回来查看是否有办法让命名空间发挥作用。这是我如何在不需要修改自动生成的类的情况下让它工作的。我最终使用 XmlTextReader 在与属性名称匹配的节点上返回所需的命名空间。有改进的余地,但我希望它对某人有所帮助。

class Program
{
static void Main(string[] args)
{
//create list to serialize
Person personA = new Person() { Name = "Bob", Age = 10, StartDate = DateTime.Parse("1/1/1960"), Money = 123456m };
List<Person> listA = new List<Person>();
for (int i = 0; i < 10; i++)
{
listA.Add(personA);
}

//serialize list to file
XmlSerializer serializer = new XmlSerializer(typeof(List<Person>));
XmlTextWriter writer = new XmlTextWriter("Test.xml", Encoding.UTF8);
serializer.Serialize(writer, listA);
writer.Close();

//deserialize list from file
serializer = new XmlSerializer(typeof(List<ProxysNamespace.Person>));
List<ProxysNamespace.Person> listB;
using (FileStream file = new FileStream("Test.xml", FileMode.Open))
{
//configure proxy reader
XmlSoapProxyReader reader = new XmlSoapProxyReader(file);
reader.ProxyNamespace = "http://myappns.com/"; //the namespace of the XmlTypeAttribute
reader.ProxyType = typeof(ProxysNamespace.Person); //the type with the XmlTypeAttribute

//deserialize
listB = (List<ProxysNamespace.Person>)serializer.Deserialize(reader);
}

//display list
foreach (ProxysNamespace.Person p in listB)
{
Console.WriteLine(p.ToString());
}

Console.ReadLine();
}
}

public class Person
{
public string Name { get; set; }
public int Age { get; set; }
public DateTime StartDate { get; set; }
public decimal Money { get; set; }
}

namespace ProxysNamespace
{
[XmlTypeAttribute(Namespace = "http://myappns.com/")]
public class Person
{
public string Name { get; set; }
public int Age { get; set; }
public DateTime Birthday { get; set; }
public decimal Money { get; set; }

public override string ToString()
{
return string.Format("{0}:{1},{2:d}:{3:c2}", Name, Age, Birthday, Money);
}
}
}

public class XmlSoapProxyReader : XmlTextReader
{
List<object> propNames;
public XmlSoapProxyReader(Stream input)
: base(input)
{
propNames = new List<object>();
}

public string ProxyNamespace { get; set; }

private Type proxyType;
public Type ProxyType
{
get { return proxyType; }
set
{
proxyType = value;
PropertyInfo[] properties = proxyType.GetProperties();
foreach (PropertyInfo p in properties)
{
propNames.Add(p.Name);
}
}
}

public override string NamespaceURI
{
get
{
object localname = LocalName;
if (propNames.Contains(localname))
return ProxyNamespace;
else
return string.Empty;
}
}
}

关于c# - 反序列化没有命名空间但在需要命名空间的类中的 XML,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2296305/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com