2010-02-12 15 views

Respuesta

8

Sí, puede combinar XmlReader con method XNode.ReadFrom; consulte el ejemplo en la documentación que utiliza C# para procesar de forma selectiva los nodos encontrados por XmlReader como XElement.

+0

brillante. Estoy desarrollando una aplicación que procesará varios archivos XML de 200M y XDocument me estaba matando. esto ha hecho una gran mejora. Gracias. –

+4

Creo que hay un error en el código de ejemplo en la página de documentación 'XNode.ReadFrom'. La instrucción 'XElement el = XElement.ReadFrom (reader) como XElement; 'debe ser' XElement el = new XElement (reader.Name, reader.Value); 'en su lugar. Tal como está, el primero de cada dos elementos 'secundarios' se omite en el archivo XML desde el que se lee. –

+0

Mi último comentario tampoco es del todo correcto; trabajando en esto ahora para mí ... –

0

Solo tenga en cuenta que tendrá que leer el archivo secuencialmente y que referir a hermanos o descendientes va a ser lento en el mejor de los casos, e imposible en el peor. De lo contrario, @MartinHonnn tiene la clave.

+0

Esta respuesta se debe eliminar y agregar como comentario. –

5

El código de ejemplo en la documentación de MSDN para el método XNode.ReadFrom es el siguiente:

class Program 
{ 
    static IEnumerable<XElement> StreamRootChildDoc(string uri) 
    { 
     using (XmlReader reader = XmlReader.Create(uri)) 
     { 
      reader.MoveToContent(); 
      // Parse the file and display each of the nodes. 
      while (reader.Read()) 
      { 
       switch (reader.NodeType) 
       { 
        case XmlNodeType.Element: 
         if (reader.Name == "Child") 
         { 
          XElement el = XElement.ReadFrom(reader) as XElement; 
          if (el != null) 
           yield return el; 
         } 
         break; 
       } 
      } 
     } 
    } 

    static void Main(string[] args) 
    { 
     IEnumerable<string> grandChildData = 
      from el in StreamRootChildDoc("Source.xml") 
      where (int)el.Attribute("Key") > 1 
      select (string)el.Element("GrandChild"); 

     foreach (string str in grandChildData) 
      Console.WriteLine(str); 
    } 
} 

Pero he encontrado que el método StreamRootChildDoc en el ejemplo tiene que ser modificado de la siguiente manera:

static IEnumerable<XElement> StreamRootChildDoc(string uri) 
    { 
     using (XmlReader reader = XmlReader.Create(uri)) 
     { 
      reader.MoveToContent(); 
      // Parse the file and display each of the nodes. 
      while (!reader.EOF) 
      { 
       if (reader.NodeType == XmlNodeType.Element && reader.Name == "Child") 
       { 
        XElement el = XElement.ReadFrom(reader) as XElement; 
        if (el != null) 
         yield return el; 
       } 
       else 
       { 
        reader.Read(); 
       } 
      } 
     } 
    } 
Cuestiones relacionadas