Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/317.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
XML反序列化C#为有效文档提供错误_C#_.net_Xml_Xml Deserialization - Fatal编程技术网

XML反序列化C#为有效文档提供错误

XML反序列化C#为有效文档提供错误,c#,.net,xml,xml-deserialization,C#,.net,Xml,Xml Deserialization,我有很多相同结构的XML文件。其中许多工作正常,但对于某些XmlSerializer,它会给我一个错误,但当我将文档放入xml验证器时,它会说文档是正确的 反序列化代码: var document = serializer.Deserialize(File.OpenRead(file)); 错误: System.InvalidOperationException: There is an error in XML document (504, 8). ---> System.Xml.Xm

我有很多相同结构的XML文件。其中许多工作正常,但对于某些XmlSerializer,它会给我一个错误,但当我将文档放入xml验证器时,它会说文档是正确的

反序列化代码:

var document = serializer.Deserialize(File.OpenRead(file));
错误:

System.InvalidOperationException: There is an error in XML document (504, 8). ---> System.Xml.XmlException: Unexpected node type Element. ReadElementString method can only be called on elements with simple or empty content. Line 504, position 8.
  at System.Xml.XmlReader.ReadElementString()
  at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationReaderPatentdocument.Read33_Claimtext(Boolean isNullable, Boolean checkType)
  at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationReaderPatentdocument.Read34_Claim(Boolean isNullable, Boolean checkType)
  at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationReaderPatentdocument.Read35_Claims(Boolean isNullable, Boolean checkType)
  at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationReaderPatentdocument.Read43_Patentdocument(Boolean isNullable, Boolean checkType)
  at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationReaderPatentdocument.Read44_patentdocument()
  --- End of inner exception stack trace ---
  at System.Xml.Serialization.XmlSerializer.Deserialize(XmlReader xmlReader, String encodingStyle, XmlDeserializationEvents events)
  at System.Xml.Serialization.XmlSerializer.Deserialize(Stream stream)
文档中出现错误的部分:

<text>12. Führungsschiene nach einem der Ansprüche 2 bis 11, dadurch gekennzeichnet, daß in den beiden Nutwänden (<b>11<i>a</i>, 11</b><i>a′)</i> einander gegenüberliegende Bohrungen (<b>14</b><i>a</i>, <b>14</b><i>a</i>′) vorgesehen sind, von denen die eine Bohrung (<b>14</b><i>a</i>′) durch das Einsatzteil (<b>15</b><i>a)</i> ver­schlossen ist.</text>
12。Führungschiene nach eine de Ansprüche 2 bis 11,dadurch gekennzeichnet,daßin den beiden Nutwänden(11a,11a′)einander gegenüberliegende Bohrungen(14a,14a′)von denen die Bohrung(14a′)durch das Einsatzteil(15a)ver schlossen ist。
我想这是因为里面有内联html标记,因为它抱怨I标记位置上的这一行

<b>11<i>a</i>, 11</b>
11a,11
但例如,根据XmlSerializer,此xml是正确的,可以对其进行反序列化:

<text>9. Führungsschiene nach Anspruch 8, dadurch gekennzeichnet, daß der Ansatz (<b>20</b>) die Zuführfläche (<b>25</b>) aufweist.</text>
9。弗伦斯切尼·纳赫·安斯普鲁奇8号,达杜尔赫·格肯尼泽尼特,安萨茨(20)号,奥夫韦斯特(25)号。

所以我的问题是,为什么xml验证器说文档是有效的,而XmlSerializer不能对其进行反序列化?是否可以在不更改文档的情况下找到解决方法?

当您指向内部HTML标记时,您是对的。 XML无效,因为在简单(文本)元素中有标记。XmlSerializer不理解并抛出错误

如果您已经生成了XML文件,那么您必须事先转义简单元素中的数据:

  • 使用HTML编码
  • 或者将其封装在CDATA标记中(
尝试序列化引起问题的实例。然后可以将序列化的输出与尝试反序列化的文件的内容进行比较。这两个XML字符串之间的差异将告诉您问题所在

下面是一个将类实例序列化为XML的快速函数:

    public static string Serialize<T>(T entity)
    {
        if (entity == null)
            return String.Empty;

        try
        {
            XmlSerializer XS = new XmlSerializer(typeof(T));
            System.IO.StringWriter SW = new System.IO.StringWriter();
            XS.Serialize(SW, entity);
            return SW.ToString();
        }
        catch (Exception e)
        {
            Logging.Log(Severity.Error, "Unable to serialize entity", e);
            return String.Empty;
        }
    }
公共静态字符串序列化(T实体)
{
if(实体==null)
返回字符串。空;
尝试
{
XmlSerializer XS=新的XmlSerializer(typeof(T));
System.IO.StringWriter SW=新的System.IO.StringWriter();
序列化(软件、实体);
返回SW.ToString();
}
捕获(例外e)
{
Logging.Log(Severity.Error,“无法序列化实体”,e);
返回字符串。空;
}
}

如果您还没有尝试过,我建议您使用该软件轻松查看这两个文件之间的差异

假设我们有以下类:

public class Foo
{
    //[XmlIgnore]
    public string Text { get; set; }
}
以及以下形式的xml:

<Foo xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <text>12. Führungsschiene nach einem der Ansprüche 2 bis 11, dadurch gekennzeichnet, daß in den beiden Nutwänden (<b>11<i>a</i>, 11</b><i>a′)</i> einander gegenüberliegende Bohrungen (<b>14</b><i>a</i>, <b>14</b><i>a</i>′) vorgesehen sind, von denen die eine Bohrung (<b>14</b><i>a</i>′) durch das Einsatzteil (<b>15</b><i>a)</i> ver­schlossen ist.</text>
</Foo>
订阅
XmlSerializer
UnknowneElement
事件

在事件处理程序中,手动将我们的属性设置为数据

private static void Xs_UnknownElement(object sender, XmlElementEventArgs e)
{
    var foo = (Foo)e.ObjectBeingDeserialized;
    foo.Text = e.Element.InnerXml;
}

请注意,属性名称不应与xml节点名称匹配(区分大小写)。只有在这种情况下,才会触发事件。如果名称匹配,请使用
XmlIgnore
属性。

应用程序中需要一组与xml文件匹配的类。序列化/反序列化不是自动的。文档不是有效的XML。它包含名为
b
i
的未知XML标记。如果要将HTML字符串包含在XML中,则必须对其进行编码document@CharlesMager检查错误消息-反序列化程序抱怨一个简单元素。调用堆栈显示反序列化程序是从XSD生成的,XSD需要
元素中的文本。XSD错误,或者序列化程序中存在错误。如果数据来自第三方,OP可能必须找到一种处理无效数据的方法data@syned该验证器没有提到XSD,只提到旧的DTD。您只是复制了该文件还是包含了有效DTD的链接?如果你只是复制了文件,结果是没有意义的。问题是,用于生成反序列化器的XSD需要
的简单文本内容。您是否基于某个示例生成了XSD?不要混淆有效和格式良好的xml!您的xml格式良好,因此XmlSerializer通常可以对其进行反序列化。但根据类的定义,您的XML无效。显然,您应该向类中添加
b
i
属性。XML无效。它在
元素中包含XML标记。当HTML标记出现在XML元素(特别是简单元素)中时,不会受到任何特殊处理。我无权访问生成这些文件的过程。这些是我的输入文件。@DarKalimHero我没有为文件添加CDATA的选项。当然,我可以对文件进行预处理,动态添加CDATA,然后对其进行反序列化。但是,如果可能的话,我想避免这种情况。在XML中包含html而无需编码或CDATA OK是可能的。你到底想做什么?您将如何处理XML?为什么要反序列化它?也许我们可以找到一些解决办法。我不是在序列化这些文档,我理解它们是作为输入的。我不确定这是否可行,但是你能用输入的数据手工编写一个实例吗?
private static void Xs_UnknownElement(object sender, XmlElementEventArgs e)
{
    var foo = (Foo)e.ObjectBeingDeserialized;
    foo.Text = e.Element.InnerXml;
}