4

我有类似于下面的 XML 的东西。我在 C# 中使用 Linq 解析它,它运行良好,直到我们得到一个没有type.

<productList>
    <product>
        <type>
            <colour>red</colour>
        </type>
        <name>First</name>
    </product>
    <product>
        <name>Second</name>
    </product>
</productList>

我正在尝试访问colour下的元素type,但是当代码到达product没有该type元素的 a 时,我收到“对象引用未设置为对象的实例”错误。

这是我目前用来访问它的代码。我试图解决这个问题的尝试让事情变得有点复杂。

productColour = products.Element("type").Descendants().FirstOrDefault() == null ? string.Empty : products.Element("type").Descendants().FirstOrDefault().Value,

我知道colour元素总是第一个在下面type,所以我可以使用.FirstOrDefault(),但使用这段代码我仍然得到同样的错误。

谁能指出我正确的方向?我也尝试过强制转换为字符串,并且还有:?? " "最后,到目前为止都无济于事。

编辑:感谢@anthony-pegram,看起来问题是我总是试图抓住后代,即使父元素不存在。所以看起来我需要在抓住孩子之前检查父元素 - 谁能指出我的方向?

4

3 回答 3

3

Elements()将返回一个 IEnumerable。如果该元素不存在,则 IEnumerable 将只是空的,并且在其上再次调用 Elements 不会产生空引用异常。下面的代码应该从 product\type 元素下提取颜色,而不会引发空引用异常。如果颜色或类型不存在,它将返回 null。

(string)product.Elements("type").Elements("colour").FirstOrDefault()
于 2012-11-19T16:26:09.547 回答
0

我会在这里使用 XPath

var xDoc = XDocument.Parse(xml);
var colour = xDoc.XPathSelectElement("//product/type/colour");
if(colour!=null)
{
    var val = colour.Value;
}
于 2012-11-19T16:20:53.080 回答
0

你有没有想过用一个属性来代替?

<productList>
    <product type="color-red">
        <name>First</name>
    </product>
    <product type="none">
        <name>Second</name>
    </product>
</productList>

没有机会返回 null 变量,因为 type 属性可以具有默认字符串值。我也认为这更整洁,但这是个人喜好。

你也可以做之<product color="red" />类的。

于 2012-11-19T16:36:35.520 回答