XStreamingElement作为XDocument的一部分

时间:2016-02-24 13:29:27

标签: c# .net xml linq-to-xml

我想写一个非常大的XML文档,所以System.Xml.Linq.XStreamingDocument似乎是理想的解决方案。

我以为我能够构造XDocument以包含XStreamingDocument,并且只有当我调用Save()时才会遍历树并且可以迭代枚举。

public void WriteXml(IEnumerable<string> lotsOfStrings, TextWriter output)
{
    var rootElement = new XElement("Root", 
       new XStreamingElement ("Strings", lotsOfStrings.Select(s => new XElement("Line", s))));

    var document = new XDocument(rootElement);
    document.Save(output);
}

但事实并非如此。只要我将XStreamingElement添加到包含元素,它就会迭代枚举并生成所有元素。

我打算将这个长元素列表嵌套到几个元素深处。在调用XmlWriter之前,是否必须使用XStreamingElement.WriteTo()手动编写包含结构?这有点单调乏味,最终我混合范式(XmlWriterSystem.Xml.Linq)。这似乎真的限制了XStreamingElement的用处。

或者我错过了构建包含可流化元素的文档的方法吗?

1 个答案:

答案 0 :(得分:3)

您在非流媒体元素(i.a。XElementXDocument)内包装的任何内容都会被迭代并立即生成。如果您将 Root 元素类型从XElement更改为XStreamingElement,则不会立即执行linq查询。您可以将XElement用于使用linq延迟生成的叶节点(例如 Line 元素),但是对于具有动态内容的任何元素,您必须使用XStreamingElement你不想过早地生成。

您可以使用单独定义的嵌套XStreamingElement构建更大的结构。我已经通过单独引入 Strings 元素在我的代码示例中演示了这一点。您也可以使用自己的 Iterators 代替linq查询来创建动态内容。

最后但并非最不重要的是,XStreamingElement有方法Save(TextWriter writer),因此您实际上也不需要XDocument

public static void WriteXml(IEnumerable<string> lotsOfStrings, TextWriter output)
{
    var stringsElement = new XStreamingElement("Strings",
        lotsOfStrings.Select(s => new XElement("Line", s)));
    var rootElement = new XStreamingElement("Root", stringsElement);

    //No XML is generated yet

    rootElement.Save(output); //Whole XML is generated and saved to output
}