C# 使用带有 Xml 命名空间的 Linq to Xml
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/2340411/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Use Linq to Xml with Xml namespaces
提问by Tim
I have this code :
我有这个代码:
/*string theXml =
@"<Response xmlns=""http://myvalue.com""><Result xmlns:a=""http://schemas.datacontract.org/2004/07/My.Namespace"" xmlns:i=""http://www.w3.org/2001/XMLSchema-instance""><a:TheBool>true</a:TheBool><a:TheId>1</a:TheId></Result></Response>";*/
string theXml = @"<Response><Result><TheBool>true</TheBool><TheId>1</TheId></Result></Response>";
XDocument xmlElements = XDocument.Parse(theXml);
var elements = from data in xmlElements.Descendants("Result")
select new {
TheBool = (bool)data.Element("TheBool"),
TheId = (int)data.Element("TheId"),
};
foreach (var element in elements)
{
Console.WriteLine(element.TheBool);
Console.WriteLine(element.TheId);
}
When I use the first value for theXml, the result is null, whereas with the second one, I have good values ...
当我为 theXml 使用第一个值时,结果为空,而使用第二个值时,我有很好的值......
How to use Linq to Xml with xmlns values ?
如何使用带有 xmlns 值的 Linq to Xml ?
采纳答案by Mike Two
LINQ to XML methods like Descendants
and Element
take an XName
as an argument. There is a conversion from string
to XName
that is happening automatically for you. You can fix this by adding an XNamespace
before the strings in your Descendants
and Element
calls. Watch out because you have 2 different namespaces at work.
LINQ to XML 方法,如Descendants
并Element
以 anXName
作为参数。有一个从string
到XName
那个的转换正在为你自动发生。您可以通过XNamespace
在Descendants
和Element
调用中的字符串之前添加一个来解决此问题。请注意,因为您有 2 个不同的命名空间在工作。
string theXml =
@"true1";
//string theXml = @"true1";
XDocument xmlElements = XDocument.Parse( theXml );
XNamespace ns = "http://myvalue.com";
XNamespace nsa = "http://schemas.datacontract.org/2004/07/My.Namespace";
var elements = from data in xmlElements.Descendants( ns + "Result" )
select new
{
TheBool = (bool) data.Element( nsa + "TheBool" ),
TheId = (int) data.Element( nsa + "TheId" ),
};
foreach ( var element in elements )
{
Console.WriteLine( element.TheBool );
Console.WriteLine( element.TheId );
}
Notice the use of ns in Descendants
and nsa in Elements
注意 ns inDescendants
和 nsa in 的使用Elements
回答by Lachlan Roche
You can pass an XNamewith a namespace to Descendants()and Element(). When you pass a string to Descendants(), it is implicitly converted to an XName with no namespace.
您可以将带有命名空间的XName传递给Descendants()和Element()。当您将字符串传递给 Descendants() 时,它会被隐式转换为没有命名空间的 XName。
To create a XName in a namespace, you create a XNamespace and concatenate it to the element local-name (a string).
要在命名空间中创建 XName,您需要创建一个 XNamespace 并将其连接到元素 local-name(一个字符串)。
XNamespace ns = "http://myvalue.com";
XNamespace nsa = "http://schemas.datacontract.org/2004/07/My.Namespace";
var elements = from data in xmlElements.Descendants( ns + "Result")
select new
{
TheBool = (bool)data.Element( nsa + "TheBool"),
TheId = (int)data.Element( nsa + "TheId"),
};
There is also a shorthand form for creating a XName with a namespace via implicit conversion from string.
还有一种通过从字符串隐式转换来创建带有命名空间的 XName 的简写形式。
var elements = from data in xmlElements.Descendants("{http://myvalue.com}Result")
select new
{
TheBool = (bool)data.Element("{http://schemas.datacontract.org/2004/07/My.Namespace}TheBool"),
TheId = (int)data.Element("{http://schemas.datacontract.org/2004/07/My.Namespace}TheId"),
};
Alternatively, you could query against XElement.Name.LocalName.
var elements = from data in xmlElements.Descendants()
where data.Name.LocalName == "Result"
回答by dotNET
I found the following code to work fine for reading attributes with namespaces in VB.NET:
我发现以下代码可以很好地读取 VB.NET 中具有命名空间的属性:
MyXElement.Attribute(MyXElement.GetNamespaceOfPrefix("YOUR_NAMESPACE_HERE") + "YOUR_ATTRIB_NAME")
Hope this helps someone down the road.
希望这可以帮助某人在路上。
回答by mike nelson
I have several namespaces listed at the top of an XML document, I don't really care about which elements are from which namespace. I just want to get the elements by their names. I've written this extension method.
我在 XML 文档的顶部列出了几个命名空间,我并不真正关心哪些元素来自哪个命名空间。我只想按名称获取元素。我写了这个扩展方法。
/// <summary>
/// A list of XElement descendent elements with the supplied local name (ignoring any namespace), or null if the element is not found.
/// </summary>
public static IEnumerable<XElement> FindDescendants(this XElement likeThis, string elementName) {
var result = likeThis.Descendants().Where(ele=>ele.Name.LocalName==elementName);
return result;
}