2013-08-02 176 views
4

如何使用C#以正確的方式獲取屬性「action」和「filename」值?C#從xml屬性獲取值

XML:

<?xml version="1.0" encoding="utf-8" ?> 
<Config version="1.0.1.1" > 
    <Items> 
    <Item action="Create" filename="newtest.xml"/> 
    <Item action="Update" filename="oldtest.xml"/> 
    </Items> 
</Config> 

C#:我不能得到屬性值,以及如何在foreach循環中獲取值?如何解決這個問題?

 var doc = new XmlDocument(); 
     doc.Load(@newFile); 
     var element = ((XmlElement)doc.GetElementsByTagName("Config/Items/Item")[0]); //null 
     var xmlActions = element.GetAttribute("action"); //cannot get values 
     var xmlFileNames= element.GetAttribute("filename"); //cannot get values 

     foreach (action in xmlActions) 
     { 
      //not working 
     } 

     foreach (file in xmlFileNames) 
     { 
      //not working 
     } 

你的代碼示例對我意味着很多。謝謝!

+1

您可能想查看[LINQ to XML](http://msdn.microsoft.com/library/bb387087.aspx)。它使得使用XML更容易。 – Corak

回答

7

您可以使用LINQ to XML。下面的查詢返回強類型項目的收集與ActionFileName屬性:

var xdoc = XDocument.Load(@newFile); 

var items = from i in xdoc.Descendants("Item") 
      select new { 
       Action = (string)i.Attribute("action"), 
       FileName = (string)i.Attribute("fileName") 
      }; 

foreach (var item in items) 
{ 
    // use item.Action or item.FileName 
} 
+0

var items = for i in xdoc (「Item」) 選擇新動作=(string)i.Attribute(「action」), FileName =(string)i.Attribute(「fileName」) };不正確的代碼語法 – user235973457

+0

@ user235973457對不起,錯字。它應該是'from'而不是'' –

+1

它的工作,非常感謝! – user235973457

3

GetElementsByTagName會發現你只有直系後代。該參數應該是只是標籤名稱,而不是整個元素的路徑。

如果要在提供XPath表達式的同時在文檔中進行搜索,請改爲使用SelectNodes

對於您的文檔,它應該是這樣的:

var element = (XmlElement)doc.SelectNodes("/Config/Items/Item")[0]; 
+0

我已經嘗試過SelectNode,但不知道如何在代碼中使用它。你能給我舉例代碼嗎? – user235973457

+0

@ user235973457:我已添加示例性呼叫;我現在不能嘗試,但我希望命名空間不會有問題。如果您遇到任何錯誤,請包括確切的錯誤消息,我或此處的任何其他人將在稍後嘗試。 –

+0

好的謝謝,我希望任何人都能幫助解決這個問題。 :) – user235973457

2

你可以實現你與LINQ to XML問什麼:

// For each element that is a child of your Items element that is named Item 
foreach (var item in XElement.Load("file.xml").Descendants("Items").Elements("Item")) 
{ 
    // If the element does not have any attributes 
    if (!item.Attributes().Any()) 
    { 
     // Lets skip it 
     continue; 
    } 

    // Obtain the value of your action attribute - Possible null reference exception here that should be handled 
    var action = item.Attribute("action").Value; 
    // Obtain the value of your filename attribute - Possible null reference exception here that should be handled 
    var filename = item.Attribute("filename").Value; 

    // Do something with your data 
    Console.WriteLine("action: {0}, filename {1}", action, filename); 
} 
2

有與問題的代碼一堆問題:
1.您正在使用的的getElementsByTagName的XPath,只需使用標籤
2.您只通過使用[0]
獲取XmlNodeCollection中的第一個XmlNode 3.由於您只有一個XmlNode,因此只會獲取用於獲取屬性的字符串結果,而不是字符串集合,你然後試圖通過
枚舉4.你的foreach是壞了,沒有類型生成的對象

這裏是將工作的一個片段:

var doc = new XmlDocument(); 
doc.Load("test.xml"); 
var items = doc.GetElementsByTagName("Item"); 

var xmlActions = new string[items.Count]; 
var xmlFileNames = new string[items.Count]; 
for (int i = 0; i < items.Count; i++) { 
    var xmlAttributeCollection = items[i].Attributes; 
    if (xmlAttributeCollection != null) { 
     var action = xmlAttributeCollection["action"]; 
     xmlActions[i] = action.Value; 

     var fileName = xmlAttributeCollection["filename"]; 
     xmlFileNames[i] = fileName.Value; 
    } 
} 

foreach (var action in xmlActions) { 
    //working 
} 

foreach (var file in xmlFileNames) { 
    //working 
} 

或者,如果你採取行動之前並不需要一個集合中的所有行動和文件名他們,你可以對for循環中的每個動作/文件名採取行動。