2010-07-09 6 views
8

Cela supprime tous les éléments du document:Suppression de nœuds de XDocument

 XDocument document = XDocument.Load(inputFile); 
     foreach (XElement element in document.Elements()) 
     { 
      element.Remove(); 
     } 
     document.Save(outputFile); 

Cela n'a aucun effet:

 XDocument document = XDocument.Load(inputFile); 
     foreach (XElement element in document.Elements()) 
     { 
      //element.Remove(); 
      foreach (XElement child in element.Elements()) 
       child.Remove(); 
     } 
     document.Save(outputFile); 

Suis-je manque quelque chose ici? Puisque ce sont toutes des références à des éléments dans le XDocument, les modifications ne devraient-elles pas prendre effet? Existe-t-il un autre moyen de supprimer des enfants imbriqués d'un XDocument?

Merci!

+0

Avez-vous débogué le code? Êtes-vous sûr que element.Elements() renvoie des éléments enfants? Je cherche juste un peu plus d'informations sur exactement ce que vous voyez arriver. – jrista

+0

@jrista Il retourne des éléments enfants, mais le problème semble être que l'énumérateur se comporte différemment après '.Remove()'. – Jake

+1

Oui, c'est ce à quoi je m'attendrais. Les énumérateurs lancent généralement des exceptions lorsque vous modifiez la collection, car ils dépendent beaucoup de la stabilité de la collection sous-jacente pour fonctionner correctement. Je suis vraiment surpris que vous puissiez continuer après avoir supprimé un noeud en utilisant un foreach/énumérateur. Je recommande généralement d'utiliser une boucle while (ou éventuellement pour ... mais c'est plus compliqué), plutôt qu'un foreach. – jrista

Répondre

18

Apparemment, lorsque vous itérer sur element.Elements(), appeler un Remove() sur l'une des causes des enfants l'énumérateur à yield break. L'itération sur element.Elements().ToList() a résolu le problème.

+0

Est-ce spécifique à XPath alors? – Neo

+0

@Neo De quelle façon? Comme l'a souligné [jirsta] (http://stackoverflow.com/users/111554/jrista), la plupart des énumérateurs se briseront lorsque la collection sous-jacente changera. – Jake

+0

Oui, je suis conscient qu'une exception InvalidOperationException se produit normalement. Ma question concerne la «rupture de rendement». Est-ce spécifique à XPath vis-à-vis du commentaire de @ jrista? – Neo

2

Voici un exemple d'une autre manière en utilisant System.Xml.XPath (modifier la requête XPath pour répondre à vos besoins):

const string xml = 
    @"<xml> 
     <country> 
      <states> 
       <state>arkansas</state> 
       <state>california</state> 
       <state>virginia</state> 
      </states> 
     </country> 
    </xml>"; 
XDocument doc = XDocument.Parse(xml); 
doc.XPathSelectElements("//xml/country/states/state[.='arkansas']").ToList() 
    .ForEach(el => el.Remove());; 
Console.WriteLine(doc.ToString()); 
Console.ReadKey(true); 
2

Lorsque vous utilisez XDocument essayez ceci:

XDocument document = XDocument.Load(inputFile); 
foreach (XElement element in document.Elements()) 
{ 
    document.Element("Root").SetElementValue(element , null); 
} 
document.Save(outputFile) 

Cordialement, Todd

Questions connexes