2014-09-02 3 views
2

Я хочу, чтобы мое заявление Linq для извлечения только customfield с имя = «Требуется» в приведенном ниже примереВыбрать узлы с определенным атрибутом, используя Linq

<root> 
    <appinfo> 
     <application app_id=1234 app_name="SomeName"> 
     <customfield name="Required" value="123" /> 
     <customfield name="Not Required" value="234" /> 
     <customfield name="Not Required" value="345" /> 
     <customfield name="Not Required" value="456" /> 
     <customfield name="Not Required" value="678" /> 
     </application> 
    </appinfo> 
    ... 
    </root> 

1234, SomeName, 123 потребности быть определена этот случай

Ниже приведено заявление, которое я пробовал. Прокомментировано Где не работает

var appAI = 
     from appinfo in doc.Root.Elements() 

     let application = appinfo.Elements().First() 
     let custom_field = application.Descendants() 

     //.Where(x => (string)x.Attribute("name") == "Required" && (string)x.Attribute("value").Value !="") 
     select new 
     { 
      app_id = (string)application.Attribute("app_id"), 
      app_name = (string)application.Attribute("app_name"), 
      app_AI = custom_field 

     }; 
+0

Если не 'x.Attribute ("имя") == "Обязательный"' 'быть x.Attribute ("имя") Значение == "Обязательный"'? – barrick

+0

Я пробовал оба. Не повезло .. – mhn

ответ

0

Посмотрите, будет ли это работать. Обратите внимание, что вы можете связать «Элементы» и некоторые другие методы расширения непосредственно с IEnumerable<T>, чтобы сделать его немного проще.

from app in doc.Elements("appinfo").Elements("application") 
from cf in app.Elements("customfield") 
where (string)cf.Attribute("name") == "Required" 
select new 
{ 
    app_id = (string)app.Attribute("app_id"), 
    app_name = (string)app.Attribute("app_name"), 
    app_AI = (string)cf.Attribute("value") 
}; 

Descendants очень редко является полезным методом, поскольку он может скрыть возможные структурные проблемы в документе. Я бы не использовал его, если бы я не выполнял проверку в другом месте (например, с XSD).

+0

Это сработало .. с незначительными изменениями. , Для моего нового XML он должен быть doc.Root.Elements. Кроме того, cf.Attribute ("value"). Значение! = "" Было добавлено условие – mhn

1

Это, казалось, работал для меня:

var results = 
    from appInfo in d.Elements() 
    let application = appInfo.Elements().First() 
    let custom_field = application.Descendants() 
     .Where(x => x.Attribute("name").Value == "Required" && x.Attribute("value").Value != "") 
     .SingleOrDefault() 
    select new 
    { 
     app_id = application.Attribute("app_id").Value, 
     app_name = application.Attribute("app_name").Value, 
     app_AI = custom_field.Attribute("value").Value 
    }; 

Я думаю, что ваша главная проблема смотрела на d.Root.Elements вместо просто d.Elements.

. Пример:https://dotnetfiddle.net/XVM1qz

+0

Я пропустил корневой тег в моем вопросе. извинения .. Я пробовал с d.Root.Elements(). Я получаю ссылку на объект не установленную ошибку – mhn

+0

странно .. Когда я пытаюсь на вашей скриптовой ссылке .. Даже после добавления корня, он отлично работает – mhn

+0

Я нашел ошибку. Это связано с тем, что для нескольких узлов нет закрывающего тега для приложения. Повторите то же самое здесь https://dotnetfiddle.net/YUoL4N – mhn

Смежные вопросы