C# 使用Linq to Xml选择Xml节点

C# 使用Linq to Xml选择Xml节点,c#,xml,lambda,linq-to-xml,C#,Xml,Lambda,Linq To Xml,我的Xml文件: <?xml version="1.0" encoding="utf-8"?> <ArrayOfCustomer xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"> <Customer> <CustomerId>1f323c97-2015-4a3d-9956-a

我的Xml文件:

<?xml version="1.0" encoding="utf-8"?>
<ArrayOfCustomer xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <Customer>
        <CustomerId>1f323c97-2015-4a3d-9956-a93115c272ea</CustomerId>
        <FirstName>Aria</FirstName>
        <LastName>Stark</LastName>
        <DOB>1999-01-01T00:00:00</DOB>
    </Customer>
    <Customer>
        <CustomerId>c9c326c2-1e27-440b-9b25-c79b1d9c80ed</CustomerId>
        <FirstName>John</FirstName>
        <LastName>Snow</LastName>
        <DOB>1983-01-01T00:00:00</DOB>
    </Customer>
</ArrayOfCustomer>  
1)
x
不是一个
XElement

2) 这是选择Xml节点的合适位置吗


3) 当然,根据
CustomerId
,您将如何找到此节点?

您不是在铸造
x
您是在铸造
x.substands()
。x、 后代()返回一个集合,因此是复数语义方法。在我的脑海中,你应该能够做
x.subjections(“CustomerId”)。FirstOrDefault()作为XElement

你的问题是
后代和
其中
返回一个
IEnumerable
而不是一个
XElement
,这是你想要的。您可以这样修复此问题:

XElement toEdit = doc.Descendants("ArrayOfCustomer")
                     .Descendants("Customer")
                     .Where(x => Guid.Parse(x.Descendants("CustomerId").Single().Value) == customer.CustomerId)
                     .FirstOrDefault();
 XElement toEdit = doc.Descendants("Customer")
                      .Where(x => (Guid)x.Element("CustomerId") == customer.CustomerId)
                      .FirstOrDefault();

我将按如下方式重新构造您的查询:

XElement toEdit = doc.Descendants("ArrayOfCustomer")
                     .Descendants("Customer")
                     .Where(x => Guid.Parse(x.Descendants("CustomerId").Single().Value) == customer.CustomerId)
                     .FirstOrDefault();
 XElement toEdit = doc.Descendants("Customer")
                      .Where(x => (Guid)x.Element("CustomerId") == customer.CustomerId)
                      .FirstOrDefault();

我首先遇到了异常:无法将类型为“WhereEnumerableTerator`1[System.Xml.Linq.XElement]”的对象强制转换为类型为“System.Xml.Linq.XElement”。这是因为我试图将IEnumerable转换为单个XElement,我在其中添加了First()扩展。现在它无法将x表示为XElement。请注意,这要求客户下只有一个CustomerId元素。如果存在0或>1,它将抛出异常。在看了他的XML之后,这可能是合适的。但有一点需要指出。@AndrewFinnell在讨论这个问题时,您将如何编辑该节点,我现在可以更新所有客户(XElement)的死者,但如何更新文件中的节点?
 XElement toEdit = doc.Descendants("Customer")
                      .Where(x => (Guid)x.Element("CustomerId") == customer.CustomerId)
                      .FirstOrDefault();