2011-09-15 85 views
1

嗨,我有以下代碼來讀取xml文件並更改特定節點的值,但我想使用xmltextreader或xmlreader來做同樣的事情,我試圖避免聲明doc.Save(System.Web.HttpContext.Current.Server.MapPath("Data/Example.xml"));,它直接引用了我的物理文件。如何使用xmltextreader或xmlreader解析和更新xml文件

XmlDocument doc = new XmlDocument(); 
        string xmlFile = System.Web.HttpContext.Current.Server.MapPath("Data/Example.xml"); 
        doc.Load(xmlFile); 
        XmlNodeList xmlnode = doc.GetElementsByTagName("value"); 
        xmlnode[0].ChildNodes[0].Value = 23; 
doc.Save(System.Web.HttpContext.Current.Server.MapPath("Data/Example.xml")); 
+0

+1但無論如何,問題看起來並無問題,使用*讀者*無法保存*任何東西,這讓我想起了我的英語語言知識。 –

回答

2

那麼東西的將不得不有一個文件的參考。然而,你可以很容易地改變你的代碼簡單地接受Stream(這必須是可讀,可寫和可搜索):

private static void ChangeDocument(Stream stream) 
{ 
    XmlDocument doc = new XmlDocument(); 
    doc.Load(stream); 
    XmlNodeList xmlnode = doc.GetElementsByTagName("value"); 
    xmlnode[0].ChildNodes[0].Value = 23; 
    stream.Position = 0; 
    doc.Save(stream); 
    stream.SetLength(stream.Position); // Truncate the file if it was longer 
} 

這有點難看,無可否認...

當然,你總是可以通過在文件名本身 - 您的通話MapPath仍然會處於一個較高水平的方法,這可能是你要實現所有:

private static void ChangeDocument(string filename) 
{ 
    XmlDocument doc = new XmlDocument(); 
    doc.Load(filename); 
    XmlNodeList xmlnode = doc.GetElementsByTagName("value"); 
    xmlnode[0].ChildNodes[0].Value = 23; 
    doc.Save(filename); 
} 

最後一個撥出 - 如果你正在使用.NET 3.5或更高版本,我強烈建議我們將LINQ to XML作爲一個更好的XML API。

+0

棘手的方式來隱藏doc.Save(...)? –

+0

然後文件的完整路徑將在另一個聲明Stream對象的代碼中,無論如何,這僅僅是使用基於文件的方法不可避免的方法 –

+0

@Artur:是的,如果你想訪問一個文件,你將需要名稱被稱爲*某處*。我認爲OP不希望它被計算*在這裏*,這可能是完全合理的。 (例如,這段代碼可以放到一個類庫中,在幾個應用程序中使用,其中'Server.MapPath'可能不合適。) –

1

使用XmlTextReader的的XmlReader ansectors更新XML數據,則不能寫,或使用的XmlTextWriter的XmlWriter祖先,OT XmlSerializer.Serialize(..)方法的替代方案。

你無法避免的發言,並一致好評,

doc.Save(System.Web.HttpContext.Current.Server.MapPath("Data/Example.xml")); 

具有直接引用你的物理文件,因爲你必須再次寫入變化的節點又回到了原點文件,otherwize必須切換您的系統從基於文件的方法(使用基於文件的數據存儲的ASP.NET網站)轉換爲數據庫驅動的方法(使用數據庫服務器的ASP.NET網站)。

作爲替代方案,在您的SQL服務器中使用您自己的XML數據,然後使用ORM的EF加載和更新它。