2010-09-02 2 views
1

Я нашел несколько примеров по этому вопросу. Некоторые из примеров даваемого способа изменить атрибут с SelectNodes() или SelectSingleNode() и другими даваемым методом для изменения атрибута с someElement.SetAttribute("attribute-name", "new value");Изменение существующего содержимого XML на C#

Но я до сих пор путаю, что, как строить отношения, если я использовал только XpathNodeItterator it?

предположил, что я определен ниже,

System.Xml.XPath.XPathDocument doc = new XPathDocument(xmlFile); 
System.Xml.XPath.XPathNavigator nav = doc.CreateNavigator(); 
System.Xml.XPath.XPathNodeIterator it; 

it = nav.Select("/Equipment/Items/SubItmes"); 
while (it.MoveNext()) 
{ 
    name = it.Current.GetAttribute("name ", it.Current.NamespaceURI); 
    int vidFromXML = int.Parse(it.Current.GetAttribute("vid", it.Current.NamespaceURI)); 
    if (vidFromXML = vid) 
    { 
    // How can I find the relation between it and element and node? I want to modify name attribute value. 
    } 
} 

Есть ли способ, как it.setAttribute(name, "newValue")?

ответ

4

От MSDN: «Объект XPathNavigator создается из класса, который реализует IXPathNavigable интерфейс, такие как классы XPathDocument и XMLDOCUMENT XPathNavigator объекты, созданные с помощью объектов XPathDocument только для чтения в то время как XPathNavigator объекты, созданные с помощью объектов XmlDocument может быть. отредактирован. Статус объекта XPathNavigator для чтения или редактирования определяется с помощью свойства CanEdit класса XPathNavigator. "

Итак, в первую очередь вам нужно использовать XmlDocument, а не XPathDocument, если вы хотите установить атрибут.

Пример изменения XML-данных с использованием XPathNavigator с использованием метода CreateNavigator для XmlDocument показан here.

Как вы увидите из примера, существует метод SetValue на вашем сайте. Текущий объект.

Вот как вы могли бы сделать это для вашего кода, с некоторыми незначительными изменениями:

 int vid = 2; 
     var doc = new XmlDocument(); 
     doc.LoadXml("<Equipment><Items><SubItems vid=\"1\" name=\"Foo\"/><SubItems vid=\"2\" name=\"Bar\"/></Items></Equipment>"); 
     var nav = doc.CreateNavigator(); 

     foreach (XPathNavigator it in nav.Select("/Equipment/Items/SubItems")) 
     { 
      if(it.MoveToAttribute("vid", it.NamespaceURI)) { 
       int vidFromXML = int.Parse(it.Value);      
       if (vidFromXML == vid) 
       { 
        // if(it.MoveToNextAttribute() ... or be more explicit like the following: 

        if (it.MoveToParent() && it.MoveToAttribute("name", it.NamespaceURI)) 
        { 
         it.SetValue("Two"); 
        } else { 
         throw new XmlException("The name attribute was not found."); 
        }     
       } 
      } else { 
        throw new XmlException("The vid attribute was not found."); 
      } 
     } 
+0

Спасибо за ваш вклад , Я изучил учебник MSDN. Я обнаружил, что метод «SetValue» использовался для обновления значения элемента, а не значения атрибута. Можно попробовать, но не удалось. Мне нужно найти способ обновить значение атрибута. –

+0

Теперь я нашел ваше обновление. Введено 'it.MoveToAttribute()'. Я попробую сейчас. Спасибо. –

+0

В .NET 2.0 нет 'var'. Я не могу использовать 'int.Parse (name)', когда передаю значение типа строки в 'name'. Выброс ** Строка ввода не была в правильном формате. **. Как я могу это исправить? –

0

Я написал метод расширения, который обеспечивает метод SetAttribute для любого XPathNavigator:

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Xml; 
using System.Xml.XPath; 

namespace My.Shared.Utilities { 
    public static class XmlExtensions { 
     public static void SetAttribute(this XPathNavigator nav, string localName, string namespaceURI, string value) { 
      if (!nav.MoveToAttribute(localName, namespaceURI)) { 
       throw new XmlException("Couldn't find attribute '" + localName + "'."); 
      } 
      nav.SetValue(value); 
      nav.MoveToParent(); 
     } 
    } 
}