2010-11-06 1 views
1

Этот запрос не работает, как я ожидаю. Кто-нибудь видит проблему?Нужна помощь с запросом XElement

Я пытаюсь получить элемент по его имени, но он ничего не возвращает. Вот конкретная часть функции мне нужна помощь с:

alt text


Update

Решение было использовать XName вместо строки. Вроде так:

var matchingElements = elements.Where(e => e.Name.Equals(XName.Get(name))); 

ответ

3

Попробуйте изменить строку:

elements.Where(e => e.Name.LocalName == name) 

LocalName часть является важной частью, так как в противном случае вы сравниваете равенство в XName с string. Помните, что XML поддерживает имена стиля «prefix: element-name». В этом примере «префикс» - это идентификатор, связанный с пространством имен, возвращаемым e.Name.Namespace, а «element-name» - это идентификатор, возвращаемый e.Name.LocalName.

+0

Интересно - у меня было ощущение, что это может иметь какое-то отношение к пространству имен, я буду исследовать дальше. Благодарю. –

1

Я думаю, вам нужно добавить корневое пространство имен к имени элемента. Вместо этого вы можете попробовать использовать метод XContainer.Descendants(XName).

2

Kirk's answer находится прямо на деньги. Я хотел указать на некоторые проблемы с вашим кодом.

Эта линия излишне подсчитывает все элементы:

var hasMatch = matchingElements.Count() > 0; 

Вы можете заменить его Any(), который завершится рано, как только элемент найден:

var hasMatch = matchingElements.Any(); 

Далее, удостоверившись, что hasMatch является true вы должны позвонить First() вместо FirstOrDefault(), так как вы знаете, что он должен иметь значение в этой точке.

Сказав, что вы могли бы на самом деле переписать код следующим образом:

var matchingElement = elements.FirstOrDefault(e => e.Name.LocalName == name); 
return (string)matchingElement; 

Здесь приведение к string возвратит значение элемента, если он был найден, в противном случае она будет возвращать null. Литой используется только в том случае, если это было null, так как вы не смогли бы использовать matchingElement.Value, который бы выбросил NullReferenceException, если элемент не был найден. Вы также должны рассмотреть возможность использования SingleOrDefault, если вы ожидаете существования только одного элемента.

+0

Спасибо за ваши комментарии! Я не знал о преимуществах функции. Любой. Я высоко оценил, что вы проводите время, обучая этим оптимизациям. –