Почему XElement падает при анализе XML-файла с помощью xmlns?
-
19-09-2019 - |
Вопрос
Итак, я пытаюсь проанализировать XML-файл:
<?xml version="1.0" encoding="utf-8" ?>
<Root>
<att1 name="bob" age="unspecified" xmlns="http://foo.co.uk/nan">
</att1>
</Root>
Используя следующий код:
XElement xDoc= XElement.Load(filename);
var query = from c in xDoc.Descendants("att1").Attributes() select c;
foreach (XAttribute a in query)
{
Console.WriteLine("{0}, {1}",a.Name,a.Value);
}
В консоль ничего не записывается, пока я не удалю xmlns="http://foo.co.uk/nan" из файла xml, после чего я получаю список имен и значений атрибутов, как и следовало ожидать, и как мне нужно. !
Редактировать:Форматирование.
Решение
Вы должны использовать одно и то же пространство имен в своем коде:
XElement xDoc= XElement.Load(filename);
XNamespace ns = "http://foo.co.uk/nan";
var query = from c in xDoc.Descendants(ns + "att1").Attributes() select c;
foreach (XAttribute a in query)
{
Console.WriteLine("{0}, {1}",a.Name,a.Value);
}
Атрибуты не принимают значения по умолчанию (xmlns=....
) пространство имен, поэтому вам не нужно их уточнять.Тег пространства имен (xmln:tags=....
) является чисто локальным по отношению к документу или использованию API, имена на самом деле всегда представляют собой пространство имен + локальное имя, поэтому вам всегда нужно указывать пространство имен.
Другие советы
Ваш звонок в Потомки запрашивает элемент с именем «att1» без пространства имен.
Если вы позвонили Descendants("{http://foo.co.uk/nan}att1")
вы бы выбрали элемент с пространством имен, но не элемент без пространства имен.
Вы можете выбрать элементы с именем «att1» в любом пространстве имен или вообще без него, например:
var query = from c in xDoc.Descendants() where c.Name.LocalName == "att1" select c.Attributes;
Вам необходимо указать пространство имен в Descendants
позвони, вот так:
XNamespace ns = "http://foo.co.uk/nan";
foreach (XAttribute a in xDoc.Descendants(ns + "att1"))
{
Console.WriteLine("{0}, {1}",a.Name,a.Value);
}