在节点下获取多个属性值

时间:2012-12-29 13:49:26

标签: c# .net xml linq linq-to-xml

我很难解析同时具有属性和后代的节点。

我需要进入客户节点并将其下面的所有内容解析为一个值,以便在网页上使用。

var contacts = from c in xdoc.Descendants("contact")
               select new Contact
               {              
                   Email = (string)c.Element("email"),
                   HomePhone = (string)c.Element("phone").Attribute("type") // ?
               };

我的XML:

    <customer>
          <contact>
            <name part="first">Rick</name>
            <name part="last">Smith</name>
            <email>rick@yahoo.com</email>
            <phone type="home">2299998989</phone>
            <phone type="work">2298887878</phone>
            <phone type="cell">2297778878</phone>
            <address type="home">
              <street line="1">4001 Coleman Rd</street>
              <street line="2">Ste. 99</street>
              <city>Tempe</city>
              <regioncode>AZ</regioncode>
              <postalcode>43444</postalcode>
            </address>
          </contact>
          <comments>Customer comments</comments>
        </customer>

        <vendor>
          <contact>
            <name part="full" type="salesperson">Joe Smith</name>
          </contact>
        </vendor>

2 个答案:

答案 0 :(得分:2)

XDocument xdoc = XDocument.Load(path_to_xml);
var customers = 
    from c in xdoc.Descendants("customer")
    let contact = c.Element("contact")        
    let names = contact.Elements("name")
    let phones = contact.Elements("phone")
    let address = contact.Element("address")
    let streets = address.Elements("street")
    select new Customer {
        Contact = new Contact {
            FirstName = (string)names.SingleOrDefault(n => (string)n.Attribute("part") == "first"),
            LastName = (string)names.SingleOrDefault(n => (string)n.Attribute("part") == "last"),
            Email = (string)contact.Element("email"),
            HomePhone = (string)phones.SingleOrDefault(p => (string)p.Attribute("type") == "home"),
            CellPhone = (string)phones.SingleOrDefault(p => (string)p.Attribute("type") == "cell"),
            WorkPhone = (string)phones.SingleOrDefault(p => (string)p.Attribute("type") == "work"),
            Address = new Address {
                    Type = (string)address.Attribute("type"),
                    StreetLine1 = (string)streets.SingleOrDefault(s => (int)s.Attribute("line") == 1),
                    StreetLine2 = (string)streets.SingleOrDefault(s => (int)s.Attribute("line") == 2),
                    City = (string)address.Element("city"),
                    RegionCode = (string)address.Element("regioncode"),
                    PostalCode = (string)address.Element("postalcode")
                }
        },
        Comments = (string)c.Element("comments")
    };

您需要以下类来保存已解析的数据:

public class Customer
{
    public Contact Contact { get; set; }
    public string Comments { get; set; }
}

public class Contact
{
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public string Email { get; set; }
    public string HomePhone { get; set; }
    public string WorkPhone { get; set; }
    public string CellPhone { get; set; }
    public Address Address { get; set; }
}

public class Address
{
    public string Type { get; set; }
    public string StreetLine1 { get; set; }
    public string StreetLine2 { get; set; }
    public string City { get; set; }
    public string RegionCode { get; set; }
    public string PostalCode { get; set; }
}

答案 1 :(得分:1)

要获得家庭电话号码,您应该使用:

HomePhone = (string)c.Elements("phone").SingleOrDefault(e => (string)e.Attribute("type") == "home");