LINQtoXML вложенные коллекции и значения? - PullRequest
0 голосов
/ 21 сентября 2010

У меня есть немного XML:

<Request>       
        <EmailAddress>string</EmailAddress>
        <Item>
            <name>FirstName</name>
            <value>John</value>
        </Item>
        <Item>
            <name>LastName</name>
            <value>Doe</value>
        </Item>
    </Request>

Мой объект:

public class TheObject{
         public string EmailAddress { get; set; }
        public string SkuNumber { get; set; }
        public string FirstName { get; set; }
        public string LastName { get; set; }
}

Я хочу использовать LINQtoXML, чтобы извлечь значения FirstName и LastName из приведенного выше XML для построения объекта. Как бы я это сделал?

Обновление: вот мой код, который я начал:

var object =
                xml.Descendants("Request").Select(
                    x =>
                    new TheObject()
                        {
                            EmailAddress = x.Element("EmailAddress").Value.ToString(),
                            SkuNumber = x.Element("SKU").Value.ToString(),
                            FirstName = ...,
                            LastName = ....

                        })

Ответы [ 3 ]

1 голос
/ 12 октября 2010

Как уже отмечали другие, если бы вы имели контроль над структурой XML, вы могли бы оптимизировать ее лучше для этого типа запросов.Однако, если вы застряли с ним и хотите обработать его в одном LINQ to XML, вы можете сделать что-то вроде следующего (для краткости я опустил обработку пустых ссылок / исключений в зависимости от вашей схемы, вы можете расширить это, чтобы охватитьэти области)

class Program
{
    static void Main(string[] args)
    {
        var requestXml = XDocument.Parse(@"<Request>       
                                            <EmailAddress>string</EmailAddress>
                                            <Item>
                                                <name>FirstName</name>
                                                <value>John</value>
                                            </Item>
                                            <Item>
                                                <name>LastName</name>
                                                <value>Doe</value>
                                            </Item>
                                            </Request>");

        var request = (from req in requestXml.Descendants("Request")
                       select new TheObject
                       {
                           FirstName = (from item in req.Descendants("Item")
                                              where item.Element("name").Value == "FirstName"
                                              select item.Element("value").Value).First(),
                           LastName = (from item in req.Descendants("Item")
                                       where item.Element("name").Value == "LastName"
                                       select item.Element("value").Value).First(),
                           EmailAddress = req.Element("EmailAddress").Value
                       }
                       ).First();

    }
}

public class TheObject
{
    public string EmailAddress { get; set; }
    public string SkuNumber { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
}

Надеюсь, это поможет с проблемой.

0 голосов
/ 21 сентября 2010

Если вам не нужен XPath, вы можете загрузить XML в XElement и затем получить элементы, например,

var requestXml = XElement.Parse(@"<Request>       
    <EmailAddress>string</EmailAddress>
    <Item>
        <name>FirstName</name>
        <value>John</value>
    </Item>
    <Item>
        <name>LastName</name>
        <value>Doe</value>
    </Item>
</Request>");

var firstNameItem = (from i in requestXml.Elements("Item").Where(x=>x.Element("name").Value == "FirstName")).FirstOrDefault() ?? new XElement("Item", new XElement("value", ""));

var lastNameItem = (from i in requestXml.Elements("Item").Where(x=>x.Element("name").Value == "LastName")).FirstOrDefault() ?? new XElement("Item", new XElement("value", ""));

var firstName = firstNameItem.Element("value").Value;
var lastName = lastNameItem.Element("value").Value;

или что-то в этом роде.

РЕДАКТИРОВАТЬ:

Если ваш xml больше похож на это, вы можете использовать XmlSerializer, чтобы перемещаться между вашим объектом и xml.

<Request>
    <EmailAddress>value</EmailAddress>
    <SkuNumber>value</SkuNumber>
    <FirstName>value</FirstName>
    <LastName>value</LastName>
</Request>
0 голосов
/ 21 сентября 2010

Объедините ваш LINQToXML с разумным использованием xpath, возможно, в своей проекции.Я не помню точный синтаксис, но ваш xpath будет выглядеть примерно так:

/Request/Item/value[../name={PropertyName}]

Вы должны заменить ваше «FirstName» или «LastName» на {PropertyName}.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...