【问题标题】:The most performant way to validate XML against XSD针对 XSD 验证 XML 的最高效方法
【发布时间】:2010-09-08 10:59:16
【问题描述】:

我得到一个带有 XML 的字符串变量,并有一个 XSD 文件。我必须根据 XSD 文件验证字符串中的 XML,并且知道有不止一种方法(XmlDocument、XmlReader、...?)。

验证后我只需要存储 XML,所以我不需要它在 XDocument 或 XmlDocument 中。

如果我想要最快的性能,该怎么做?

【问题讨论】:

    标签: c# .net xml xsd xml-validation


    【解决方案1】:

    其他人已经提到了 XmlReader 类来进行验证,我不会进一步详细说明。

    您的问题没有指定太多上下文。您会重复对多个 xml 文档进行此验证,还是只进行一次?我正在阅读一个场景,您只是验证大量 xml 文档(来自第三方系统?)并将它们存储以供将来使用。

    我对性能搜索的贡献是使用编译后的XmlSchemaSet,这将是线程安全的,因此多个线程可以重用它而无需再次解析 xsd 文档。

    var xmlSchema = XmlSchema.Read(stream, null);
    var xmlSchemaSet = new XmlSchemaSet();
    xmlSchemaSet.Add(xmlSchema);
    xmlSchemaSet.Compile();
    
    CachedSchemas.Add(name, xmlSchemaSet);
    

    【讨论】:

    • 是的,我验证并存储了来自第三方系统的大量 xml 文档以供以后使用。 XSD 始终是相同的,因此非常感谢您的提示,编译模式集,谢谢!
    • 本例中的CachedSchemas 是什么?
    • 只是一个 IDictionary 用于缓存结果。
    • 为什么你认为 XmlSchemaSet 是线程安全的? blogs.msdn.com/b/xmlteam/archive/2009/04/27/…
    • @RichB,这个例子就像我描述的那样工作。初始化 XmlSchemaSet,对其进行编译,然后从多个线程中使用它。但是不,我在我能找到的任何文档中都没有支持我所说的内容。
    【解决方案2】:

    我会选择带有 XmlReaderSettings 的 XmlReader,因为不需要在内存中加载完整的 XML。对于大型 XML 文件,它会更有效。

    【讨论】:

      【解决方案3】:

      我认为最快的方法是使用 XmlReader 在文档被读取时对其进行验证。这使您可以仅通过一次验证文档:http://msdn.microsoft.com/en-us/library/hdf992b8.aspx

      【讨论】:

        【解决方案4】:

        使用配置为执行验证的XmlReader,源为TextReader

        如果您不想依赖输入文档中的声明(使用XmlReaderSettings.Schemas 属性),您可以手动指定XmlReader 要使用的XSD

        开始(假设输入文档中的 XSD 实例声明)是:

        var settings = new XmlReaderSettings {
           ConformanceLevel = ConformanceLevel.Document,
           ValidationType = ValidationType.Schema,
           ValidationFlags = XmlSchemaValidationFlags.ProcessSchemaLocation |
                             XmlSchemaValidationFlags.ProcessInlineSchema,
        };
        
        int warnings = 0;
        int errors = 0;
        settings.ValidationEventHandler += (obj, ea) => {
           if (args.Severity == XmlSeverityType.Warning) {
              ++warnings;
           } else {
              ++errors;
           }
        };
        
        XmlReader xvr = XmlReader.Create(new StringReader(inputDocInString), settings);
        
        try {
           while (xvr.Read()) {
              // do nothing
           }
        
           if (0 != errors) {
              Console.WriteLine("\nFailed to load XML, {0} error(s) and {1} warning(s).", errors, warnings);
           } else if (0 != warnings) {
              Console.WriteLine("\nLoaded XML with {0} warning(s).", warnings);
           } else {
              System.Console.WriteLine("Loaded XML OK");
           }
        
           Console.WriteLine("\nSchemas loaded durring validation:");
           ListSchemas(xvr.Schemas, 1);
        
        } catch (System.Xml.Schema.XmlSchemaException e) {
           System.Console.Error.WriteLine("Failed to read XML: {0}", e.Message);
        } catch (System.Xml.XmlException e) {
           System.Console.Error.WriteLine("XML Error: {0}", e.Message);
        } catch (System.IO.IOException e) {
           System.Console.Error.WriteLine("IO error: {0}", e.Message);
        }
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2012-04-19
          • 1970-01-01
          • 1970-01-01
          • 2018-10-09
          • 2012-09-20
          • 2011-10-12
          • 2011-07-18
          • 2011-01-24
          相关资源
          最近更新 更多