我再次对XDocument / Linq的误解感到难过。对于下面的XML,我在代码中将nameEn
和provinceCode
作为变量。我正在尝试识别code
(例如,s0000002
)和nameFr
,因为我有其他两个元素。 provinceCode
和NameEn
组合在XML中是唯一的(无重复)。
<siteList>
<site code="s0000001">
<nameEn>Edmonton</nameEn>
<nameFr>Edmonton</nameFr>
<provinceCode>AB</provinceCode>
</site>
<site code="s0000002">
<nameEn>Algonquin Park</nameEn>
<nameFr>Parc Algonquin</nameFr>
<provinceCode>ON</provinceCode>
</site>
...
</siteList>
这是我正在尝试的代码(我的XML在“已加载”的XDocument中:
selectedProvince = "ON";
selectedCity = "Algonquin Park";
strSiteCode = loaded.Descendants("site")
.Where(x => x.Element("provinceCode").Value == selectedProvince)
.Where(x => x.Element("nameEn").Value == selectedCity)
.Select(x => x.Element("code").Value)
.ToString();
strNameFR = loaded.Descendants("site")
.Where(x => x.Element("provinceCode").Value == selectedProvince)
.Where (x => x.Element("nameEn").Value == selectedCity)
.Select(x => x.Element("nameFr").Value)
.ToString();
字符串strSiteCode
返回:System.Linq.Enumerable+WhereSelectEnumerableIterator
2 [System.Xml.Linq.XElement,System.String] and
strNameFR returns
“”`。
我无法弄清楚工作代码应该是什么样子。谢谢你的帮助。
道格
答案 0 :(得分:1)
尝试
var result = loaded.Descendants("site")
.Where(x => (x.Element("provinceCode").Value == selectedProvince) &&
(x.Element("nameEn").Value == selectedCity) )
.Select(x => x.Element("code").Value)
.SingleOrDefault();
if (result != null)
{
strSiteCode = result.ToString();
}
Select()
调用返回一个集合(在您的情况下恰好只有一个元素)。因此,您必须致电SingleOrDefault()
(或Single()
)才能获得该项目。此外,我删除了第二个Where()
并将条件包含在第一个Where()
。
答案 1 :(得分:1)
请记住,“x.Element(...)”方法可能会返回null,因此在其上访问“Value”将导致null ref。这假设您的xml可能总是具有provinceCode或nameEn。如果是这样,你就不会有问题,但是你不想在发布代码中放置那个可能的null ref ex。以下解决了null ref问题。
var site = loaded
.Descendants("site")
.FirstOrDefault(x => (string)x.Element("provinceCode") == selectedProvince &&
x => (string)x.Element("nameEn") == selectedCity);
if (site == null)
{
return
}
var siteCode = (string)site.Attribute("code");
var nameFr = (string)site.Element("nameFr");
答案 2 :(得分:0)
我可能会这样重写:
<site>
节点列表code
属性和nameFr
元素代码看起来像这样:
// determine the matching list of <site> nodes ...
var selectedSites = loaded
.Descendants("site")
.Where(x => x.Element("provinceCode").Value == selectedProvince)
.Where(x => x.Element("nameEn").Value == selectedCity);
// iterate over all matching <site> nodes
foreach (var site in selectedSites)
{
// grab the code attribute and nameFr element from <site> node
var siteCode = site.Attribute("code").Value;
var nameFR = site.Element("nameFr").Value;
}