[英]How to read from an XmlReader without moving it forwards?
我得到了這個場景:
while (reader.Read())
{
if (reader.NodeType == XmlNodeType.Element && reader.Name == itemElementName)
{
XElement item = null;
try
{
item = XElement.ReadFrom(reader) as XElement;
}
catch (XmlException ex)
{
//log line number and stuff from XmlException class
}
}
}
在上面的循環中,我將某個節點 (itemElementName) 轉換為 XElement。
某些節點將是良好的 XML,並且會進入 XElement,但是,有些則不會。
在 CATCH 中,我不僅想捕獲標准的 XmlException 內容……我還想捕獲當前 Xml 和字符串的提取物。
但是,如果我在將節點傳遞給 XElement 之前在節點上執行任何類型的 READ 操作,它會將讀取器向前移動。
如何在不干擾閱讀器位置的情況下獲取閱讀器 OuterXml 內容的“快照”?
實際上 ReadSubtree 將返回一個“包裝”原始閱讀器的閱讀器。 因此,通讀新書最終也會推進原書。 您必須將 XmlReader 視為僅向前閱讀器,它根本無法返回。 至於您的場景,您可以詢問讀者在輸入文件中的位置,而不是試圖記住部分 XML。 只需將其轉換為 IXmlLineInfo 接口,它就有返回行和位置的方法。 使用它,您可以記住一些起始位置(在相關元素之前),然后是錯誤的結束位置。 然后從輸入文件中以純文本形式讀取該部分。
另一個想法:讀取外部 XML(使閱讀器前進),然后從這個 XML 創建一個新的閱讀器,它允許您“返回”並處理當前節點的元素。
while (r.ReadToFollowing("ParentNode"))
{
parentXml = r.ReadOuterXml();
//since ReadOuterXml() advances the reader to the next parent node, create a new reader to read the remaining elements of the current parent
XmlReader r2 = XmlReader.Create(new StringReader(parentXml));
r2.ReadToFollowing("ChildNode");
childValue = r2.ReadElementContentAsString();
r2.Close();
}
不要在閱讀器上使用任何“讀取”操作 - 正如您所發現的,這會推進它。 使用對reader.HasValue
和reader.Value
等屬性的調用來檢查內容。 在對象瀏覽器中查找“XmlReader”,您可以讀取很多屬性。
編輯:我認為沒有一種簡單的方法可以簡單地獲取 XML,可能是因為當前節點本身可能不是有效的 XML,例如 XmlWhiteSpace、XmlText 節點甚至 XmlAttribute。
我所做的只是將元素讀入 XmlDocument,然后讀取它。 就我而言,我必須將流文檔轉換為 HTML。 我必須讀取一個內部元素來為父 HTML 元素分配一個“樣式”。
事實上,盡管 Vitek Karas MSFT 是對的,但 Helena Kupkova 在https://msdn.microsoft.com/en-us/library/aa302292.aspx上發布了一個靈巧的小型 XML 書簽閱讀器。 這允許使用緩存向后退。
與 ReadSubtree 類似的東西
using (XmlReader reader = XmlReader.Create(new StringReader(xml)))
{
reader.MoveToContent();
while (reader.Read())
{
switch (reader.NodeType)
{
case XmlNodeType.Element:
if (reader.Name == "Field") // for example i need to read node field
{
XmlReader inner = reader.ReadSubtree(); // the reader stays in the same position
XElement El = XElement.Load(inner) as XElement;
inner.Close();
}
}
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.