2012-06-04 4 views
2

J'ai actuellement un format de fichier XML qui ressemble à ceci (les espaces et ellipses ajouté pour une meilleure lisibilité):C# LINQ to XML - Parse Nested Liste des objets

<root> 
    <Module>   //Start with list of Modules 
     <ModuleParams> 
     </ModuleParams> 
    </Module> 
    ... 

    <DetectLine>  //Now a list of DetectLines 
     <DetectLineParams> 
     </DetectLineParams> 

     <Channels> //List of Channels embedded in each DetectLine 
      <Channel> 
       <ChannelParams> 
       </ChannelParams> 
      </Channel> 
      ... 

     </Channels> 
    </DetectLine> 
    ... 

</root> 

classes structurées comme suit:

public class Module 
{ 
    public ModuleParams { get; set; } 
} 

public class DetectLine 
{ 
    public DetectLineParams { get; set; } 
    public List<Channel> Channels { get; set; } 
} 

public class Channel 
{ 
    public ChannelParams { get; set; } 
} 

La liste des Modules et DetectLines est facile à analyser avec Linq to XML. Cependant, l'analyse de la liste des chaînes pour chaque DetectLine n'est pas aussi évidente pour moi. Cela peut-il être fait avec Linq to XML? Je préférerais ne pas avoir à restructurer les choses pour travailler avec un XMLSerializer.

code initial (OpenXML est un OpenFileDialog déjà vérifié pour un bon nom de fichier.):

List<Module> myModules; 
List<DetectLine> myDetectLines; 
XDocument config = XDocument.Load(openXML.FileName); 

myModules = 
     (from myElements in config.Descendants("Module") 
      select new Module() 
      { 
       ModuleParam1 = (string)myElements.Element("ModuleParam1"), 
       ModuleParam2 = (string)myElements.Element("ModuleParam2"), 
       ... 
      }).ToList<Module>(); 

myDetectLines = 
      (from myElements in config.Descendants("DetectLine") 
      select new DetectLine() 
      { 
       DetectLineParam1 = (string)myElements.Element("ModuleParam1"), 
       DetectLineParam2 = (string)myElements.Element("ModuleParam2"), 
       ... 

       // ?? Add Channels list here somehow... 
      }).ToList<DetectLine>(); 
+0

Donner utiliser votre code pour les modules et DetectLines – MarcinJuraszek

+0

Mon raisonnement pour garder les classes est si général parce que les paramètres réels sont à moi (c'est un fichier de configuration pour mon programme que je définis et sauvegarde.) Le format le rend facile à lire/déboguer/écrire manuellement. J'ai ajouté ma méthodologie d'analyse actuelle pour montrer ce que je cherche. Je n'ai pas besoin de quelqu'un pour résoudre le XML ou les classes elles-mêmes, juste des conseils sur l'analyse de la requête Linq. – Bandoth

Répondre

2

Avec

XElement detectLine = XElement.Parse(@"<DetectLine>  
     <DetectLineParams> 
     </DetectLineParams> 

     <Channels>  
      <Channel> 
       <ChannelParams> 
       </ChannelParams> 
      </Channel> 
      ... 

     </Channels> 
    </DetectLine> 
"); 

vous pouvez le faire par exemple

DetectLine dl1 = new DetectLine() { 
    DetectLineParams = ..., 
    Channels = (from channel in detectLine.Element("Channels").Element("Channel") 
      select new Channel() { 
       ChannelParams = new ChannelParams() { ... = channel.Element("ChannelParams").Value } 
      }).ToList(); 

Nous avons vraiment besoin de voir plus de code de classe C# concret pour épeler comment configurer la requête complète.

[modifier] Pour s'adapter avec le code que vous avez maintenant affiché:

myDetectLines = 
      (from myElements in config.Descendants("DetectLine") 
      select new DetectLine() 
      { 
       DetectLineParam1 = (string)myElements.Element("ModuleParam1"), 
       DetectLineParam2 = (string)myElements.Element("ModuleParam2"), 
       ... 

       Channels = (from channel in myElements.Element("Channels").Element("Channel") 
       select new Channel() { 
        ChannelParams = new ChannelParams() { ... = channel.Element("ChannelParams").Value } 
       }).ToList(); 
      }).ToList<DetectLine>(); 
+0

Il y a plusieurs DetectLines définies dans le fichier XML. Cela m'oblige à créer une liste de DetectLines où chaque DetectLine a une liste de Canaux (juste ajouté ma méthode d'analyse initiale pour expliquer ce que je veux dire). – Bandoth

+0

Comment ai-je manqué ça? Leçon apprise: Ne codez jamais sur un estomac vide. Merci beaucoup monsieur! – Bandoth