[英]Recursively Query XML with Linq
<tok id="9993" type="group">
<tok id="144" type="atom" soff="686" eoff="693">
<txt>popular</txt>
</tok>
<tok id="145" type="group">
<tok id="144" type="atom" soff="686" eoff="693">
<txt>movie</txt>
</tok>
<tok id="145" type="atom" soff="697" eoff="703">
<txt>characters</txt>
</tok>
</tok>
</tok>
我有一個XML文檔,我需要獲取soff和eoff的值,但這些值可以嵌套。 我嘗試過使用SelectMany(),但我做錯了。 以上是該文件的摘錄。 我基本上想得到所有類型為“atom”的“tok”,以便我可以從每個中獲取我需要的兩個值。 我的查詢是這樣的:
var queryHeadsTails2 = from h in xmlDoc.Root.Descendants("tok")
where (h.Attribute("id").Value == elem.entityID && h.Attribute("type").Value == "group")
select h;
我可以使用SelectMany來獲取type =“atom”的所有行,還是有更好的方法?
答案如下
var groups = xmlDoc.Descendants("tok").Where(x => (string)x.Attribute("type") == "group" && x.Elements("tok").Where(y => (string)y.Attribute("type") == "atom").Any()).Select(x => new {
id = (string)x.Attribute("id"),
atoms = x.Elements("tok").Where(y => (string)y.Attribute("type") == "atom").ToList()
}).ToList();
非常接近,但它在這一部分失敗了(試圖獲得組ID 153527的eoff和soff):
<tok id="153619" type="group">
<tok id="80" type="atom" soff="388" eoff="390">
<txt>in</txt>
</tok>
<tok id="153527" type="group">
<tok id="153526" type="group">
<tok id="81" type="atom" soff="391" eoff="396" no-space="true">
<txt>today</txt>
</tok>
<tok id="82" type="atom" soff="396" eoff="398">
<txt>'s</txt>
</tok>
</tok>
<tok id="128206" type="group">
<tok id="6360" type="group">
<tok id="83" type="atom" soff="399" eoff="404">
<txt>action</txt>
</tok>
<tok id="84" type="atom" soff="405" eoff="409">
<txt>movie</txt>
</tok>
</tok>
<tok id="85" type="atom" soff="410" eoff="418" no-space="true">
<txt>industry</txt>
</tok>
</tok>
</tok>
</tok>
在我得到我想要的小組后,有沒有辦法讓它變平? 有點像我從上面開始的地方?
試試以下:
var groups = doc.Descendants("tok").Where(x => (string)x.Attribute("type") == "group" && x.Elements("tok").Where(y => (string)y.Attribute("type") == "atom").Any()).Select(x => new { id = (string)x.Attribute("id"), atoms = x.Elements("tok").Where(y => (string)y.Attribute("type") == "atom").ToList() }).ToList();
如果VB'ers找到這篇文章......
首先是一些測試數據
Dim xe As XElement
'to load
' xe = XElement.Load("path / URI")
'for testing
xe = <tok id="9993" type="group">
<tok id="144" type="atom" soff="687" eoff="693">
<txt>popular</txt>
</tok>
<tok id="145" type="group">
<tok id="144" type="atom" soff="686" eoff="693">
<txt>movie</txt>
</tok>
<tok id="145" type="atom" soff="697" eoff="703">
<txt>characters</txt>
</tok>
</tok>
</tok>
然后選擇具有@type =“atom”的元素的代碼
Dim ie As IEnumerable(Of XElement) = xe...<tok>.Where(Function(el) el.@type = "atom")
最后檢查每個選定的元素
For Each el As XElement In ie
Debug.WriteLine("soff = {0}, eoff = {1}", el.@soff, el.@eoff)
Next
非常感謝你的幫助。 這讓我想到了這個似乎觸及所有情況:
var groups = from h in xmlDoc.Root.Descendants("tok")
where (h.Attribute("id").Value == elem.entityID && h.Attribute("type").Value == "group")
select new
{
id = h.Attribute("id").Value,
atoms = h.Descendants("tok").Where(y => (string)y.Attribute("type") == "atom").ToList()
};
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.