C# 使用变量XML元素从XSD反序列化XML

C# 使用变量XML元素从XSD反序列化XML,c#,xml,xsd,deserialization,C#,Xml,Xsd,Deserialization,我得到了一个XSD文件,它表示大量元素和相关属性。我已经使用xsd.exe创建了一个CS类 问题是创建的xml可以包含任何或所有元素和属性 XML示例: <App action="A" id="1" validate="yes"><ProductType id="5885"/><SpecType id="221"/><Qty>1</Qty><PartType id="7212"/><Part>456789<

我得到了一个XSD文件,它表示大量元素和相关属性。我已经使用xsd.exe创建了一个CS类

问题是创建的xml可以包含任何或所有元素和属性

XML示例:

<App action="A" id="1" validate="yes"><ProductType id="5885"/><SpecType id="221"/><Qty>1</Qty><PartType id="7212"/><Part>456789</Part></App>
<App action="A" id="2" validate="yes"><ProductType id="5883"/><Qty>1</Qty><PartType id="7211"/><Part>132465</Part></App>
}

因此,我的问题是如何根据上面的星号(*)行检查空/不存在的元素

我不能以任何方式更改xsd或源XML文件,因为它们是由主要制造商生产的

如果你需要更多信息,请告诉我


谢谢!Brad

一旦有了XSD,就可以使用数据集而不是XML读取器。然后创建了一些自动方法来检查空值,如下面的示例所示

这个例子中,CalculationAnalysisDS是XSD

        CalcualtionAnalysisDS ds = new CalcualtionAnalysisDS();
        ds.ReadXml("calc.xml");

        foreach (CalcualtionAnalysisDS.ReportRow row in ds.Report.Rows)
        {
            if (row.IsBestSHDSLDesignClassNull)
            {

            }
        }

抱歉,XSD.EXE和XML序列化不会像那样处理XML

创建这种性质的XML是因为有人认为人类应该很容易阅读和输入。他们不考虑机器是否能够使用它们。这是一个你现在必须为之付出代价的错误


您所能做的最好的事情是创建一个XSLT,将元素放入某种规范的顺序中,然后创建一个表示该顺序的XSD,并从XSD中创建类。

Hi Darvindave,谢谢您的回答。我想这是我需要走的路线,但是当我尝试使用MSDataSetGenerator时,它在“自定义工具错误:无法生成代码。未定义的数据类型:'token.”上出现了中断。所以这听起来像是与我上面的帖子无关的另一个错误,但是有什么想法吗?我还尝试了xsd.exe file.xsd/d,结果也一样。-BradI通常只需将我的XSD拖放到VisualStudio中,代码就会自动创建。您可以尝试使用xsd.exe从xml创建xsd,只是为了再次检查xsd是否正确。“c:\Program Files\Microsoft SDK\Windows\v7.0A\bin\xsd”Something.xml/l:CS/classes/uri:/l:CS有什么问题?xsd是否对SpecType(即xsd.exe生成的对象包含可为空的SpecType,例如int?或字符串)说“minOccurs=”0“?如果是这样,为什么(*)行不起作用?有什么例外/问题?如果xsd没有说“minOccurs=”0“,我希望反序列化会崩溃。嗨,Martin,它确实有:。不知道为什么会在那条线上中断。看起来应该这样,但可能是我的语法不起作用……我同意。数据绑定适用于简单的常规模式。模式越大,数据越“半结构化”,使用数据绑定就越笨拙和麻烦;XSLT和XQuery更适合处理此类数据。好的,非常好,伙计们,谢谢。我投票支持这个答案,只是为了改变方向。这是其中一个解决方案,他们咨询了除开发人员以外的所有人。
        CalcualtionAnalysisDS ds = new CalcualtionAnalysisDS();
        ds.ReadXml("calc.xml");

        foreach (CalcualtionAnalysisDS.ReportRow row in ds.Report.Rows)
        {
            if (row.IsBestSHDSLDesignClassNull)
            {

            }
        }