【问题标题】:C# XML Serializer Nested Elements Access ObjectsC# XML 序列化器嵌套元素访问对象
【发布时间】:2018-10-23 23:08:32
【问题描述】:

我有一个由 XSD.exe 工具生成的 XSD。我正在从 Excel 工作表加载数据并填充数据表,然后我想将该数据保存到 XML 文件中。如何序列化嵌套元素?

在我的架构中:(在 Providers 下可以有多个 Provider,在 ProviderSites 下可以有多个 ProviderSite)

<xs:element name="Providers">
 <xs:complexType>
  <xs:sequence>
    <xs:element maxOccurs="unbounded" name="Provider">
      <xs:complexType>
        <xs:all>
          <xs:element minOccurs="0" name="FederalTaxIdentifier" type="xs:string" />
          <xs:element minOccurs="0" name="ProviderName" type="xs:string" />
          <xs:element minOccurs="0" name="ContractualRelationshipCode" type="xs:string" />
          <xs:element minOccurs="0" name="ProviderSites">
            <xs:complexType>
              <xs:sequence>
                <xs:element maxOccurs="unbounded" name="ProviderSite">
                  <xs:complexType>
                    <xs:all>
                      <xs:element minOccurs="0" name="SiteIdentifier" type="xs:string" />
                      <xs:element minOccurs="0" name="SiteName" type="xs:string" />
                      <xs:element minOccurs="0" name="LicenseTypeCode" type="xs:string" />
                      <xs:element minOccurs="0" name="OpenDate" type="xs:string" />
                      <xs:element minOccurs="0" name="CloseDate" type="xs:string" />
                      <xs:element minOccurs="0" name="DirectorPrefixName" type="xs:string" />
                      <xs:element minOccurs="0" name="DirectorFirstName" type="xs:string" />
                      <xs:element minOccurs="0" name="DirectorMiddleInitial" type="xs:string" />
                      <xs:element minOccurs="0" name="DirectorLastName" type="xs:string" />
                      <xs:element minOccurs="0" name="DirectorPhoneNumber" type="xs:string" />
                      <xs:element minOccurs="0" name="NationalProviderIdentifier" type="xs:string" />
                      <xs:element minOccurs="0" name="WebAddress" type="xs:string" />
                    </xs:all>
                  </xs:complexType>
                </xs: element>
            </xs:complexType>
        </xs:all>   
    </xs:element>       
  </xs:sequence>

在我的 c# 中,我创建了元素 Providers->Provider 的新实例

ProvidersProvider prov = new ProvidersProvider();

我访问一个对象并将其设置到我的数据表中的单元格

prov.FederalTaxIdentifier = DtRow.ItemArray[0].ToString();

然后将其序列化为xml

serializer.Serialize(writer, prov);

试图弄清楚如何访问和添加其他元素,例如 Providers->Provider->ProviderSites->ProviderSite->SiteIdentifier

更新 我在 xsd 中添加了一个 xs:choice 元素并重新生成了该类。 我该如何设置这些元素?

<xs:element minOccurs="0" name="ProviderSitePhones">
    <xs:complexType>
        <xs:sequence>
            <xs:element maxOccurs="unbounded" name="ProviderSitePhone">
                <xs:complexType>
                    <xs:sequence>
                       <xs:choice maxOccurs="unbounded">
                          <xs:element minOccurs="0" name="TypeCode" type="xs:string" />
                           <xs:element minOccurs="0" name="PhoneNumber" type="xs:string" />
                        </xs:choice>
                    </xs:sequence>
                    <xs:attribute name="action" type="xs:string" use="optional" />
                </xs:complexType>
            </xs:element>
       </xs:sequence>
   </xs:complexType>
</xs:element>

在 XSD 类中:

/// <remarks/>
[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.6.1055.0")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(AnonymousType=true)]
public partial class ProvidersProviderProviderSiteProviderSitePhone {

    private string[] itemsField;

    private ItemsChoiceType[] itemsElementNameField;

    private string actionField;

    /// <remarks/>
    [System.Xml.Serialization.XmlElementAttribute("PhoneNumber", typeof(string))]
    [System.Xml.Serialization.XmlElementAttribute("TypeCode", typeof(string))]
    [System.Xml.Serialization.XmlChoiceIdentifierAttribute("ItemsElementName")]
    public string[] Items {
        get {
            return this.itemsField;
        }
        set {
            this.itemsField = value;
        }
    }

    /// <remarks/>
    [System.Xml.Serialization.XmlElementAttribute("ItemsElementName")]
    [System.Xml.Serialization.XmlIgnoreAttribute()]
    public ItemsChoiceType[] ItemsElementName {
        get {
            return this.itemsElementNameField;
        }
        set {
            this.itemsElementNameField = value;
        }
    }

    /// <remarks/>
    [System.Xml.Serialization.XmlAttributeAttribute()]
    public string action {
        get {
            return this.actionField;
        }
        set {
            this.actionField = value;
        }
    }
}

/// <remarks/>
[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.6.1055.0")]
[System.SerializableAttribute()]
[System.Xml.Serialization.XmlTypeAttribute(IncludeInSchema=false)]
public enum ItemsChoiceType {

    /// <remarks/>
    PhoneNumber,

    /// <remarks/>
    TypeCode,
}

在我的 Program.cs 中,我有:

ProviderSitePhones = provider.Value.Select(ProviderSitePhone => new ProvidersProviderProviderSiteProviderSitePhone()
{

}).ToArray()

【问题讨论】:

    标签: c# xml xsd schema xml-serialization


    【解决方案1】:

    试试这样的代码:

    using System;
    using System.Collections.Generic;
    using System.Collections;
    using System.Linq;
    using System.Text;
    using System.Data;
    using System.Xml;
    using System.Xml.Serialization;
    
    namespace ConsoleApplication1
    {
        class Program
        {
            const string FILENAME = @"c:\temp\test.xml";
            static void Main(string[] args)
            {
    
                DataTable dt = new DataTable();
                dt.Columns.Add("FederalTaxIdentifier", typeof(string));
                dt.Columns.Add("ProviderName", typeof(string));
                dt.Columns.Add("ContractualRelationshipCode", typeof(string));
                dt.Columns.Add("SiteIdentifier", typeof(string));
                dt.Columns.Add("SiteName", typeof(string));
                dt.Columns.Add("LicenseTypeCode", typeof(string));
                dt.Columns.Add("OpenDate", typeof(string));
                dt.Columns.Add("CloseDate", typeof(string));
                dt.Columns.Add("DirectorPrefixName", typeof(string));
                dt.Columns.Add("DirectorFirstName", typeof(string));
                dt.Columns.Add("DirectorMiddleInitial", typeof(string));
                dt.Columns.Add("DirectorLastName", typeof(string));
                dt.Columns.Add("DirectorPhoneNumber", typeof(string));
    
    
                dt.Rows.Add(new object[] { "123", "alpha", "100", "1000", "abc", "code1","1/1/2000", "2/1/2000", "Mr.", "John", "L", "Smith", "800-555-1234"});
                dt.Rows.Add(new object[] { "123", "alpha", "100", "1001", "abc", "code1", "1/1/2000", "2/1/2000", "Mrs.", "Mary", "L", "Smith", "800-555-1234" });
                dt.Rows.Add(new object[] { "123", "alpha", "100", "1001", "abc", "code1", "1/1/2000", "2/1/2000", "Mr.", "Harry", "L", "Smith", "800-555-1234" });
                dt.Rows.Add(new object[] { "456", "beta", "100", "2000", "abc", "code1", "1/1/2000", "2/1/2000", "Mr.", "John", "L", "Smith", "800-555-1234" });
                dt.Rows.Add(new object[] { "456", "beta", "100", "2001", "abc", "code1", "1/1/2001", "2/1/2001", "Mr.", "Ralph", "L", "Smith", "800-555-1234" });
                dt.Rows.Add(new object[] { "456", "beta", "100", "2002", "abc", "code1", "1/1/2000", "2/1/2000", "Mr.", "Brutus", "L", "Smith", "800-555-1234" });
                dt.Rows.Add(new object[] { "789", "gama", "100", "3000", "abc", "code1", "1/1/2000", "2/1/2000", "Mrs.", "Ronda", "L", "Smith", "800-555-1234" });
                dt.Rows.Add(new object[] { "789", "gama", "100", "3001", "abc", "code1", "2/1/2000", "3/1/2000", "Mr.", "George", "L", "Smith", "800-555-1234" });
                dt.Rows.Add(new object[] { "789", "gama", "100", "3002", "abc", "code1", "3/1/2000", "4/1/2000", "Mrs.", "Linda", "L", "Smith", "800-555-1234" });
                dt.Rows.Add(new object[] { "789", "gama", "100", "3003", "abc", "code1", "4/1/2000", "5/1/2000", "Mrs.", "Sally", "L", "Smith", "800-555-1234" });
    
                var dict = 
                    dt.AsEnumerable()
                    .GroupBy(x => x.Field<string>("FederalTaxIdentifier"), y => y)
                              .ToDictionary(x => x.Key, y => y
                                  .GroupBy(a => a.Field<string>("SiteIdentifier"), b => b)
                                  .ToDictionary( a => a.Key, b => b.FirstOrDefault()));
    
    
    
    
                Providers providers = new Providers();
    
                providers.Provider = dict.Select(provider => new ProvidersProvider()
                {
                    FederalTaxIdentifier = provider.Key,
                    ProviderName = provider.Value.FirstOrDefault().Value.Field<string>("ProviderName"),
                    ContractualRelationshipCode = provider.Value.FirstOrDefault().Value.Field<string>("ContractualRelationshipCode"),
                    ProviderSites = provider.Value.Select(site => new ProvidersProviderProviderSite()
                    {
                        SiteIdentifier = site.Key,
                        SiteName = site.Value.Field<string>("SiteName"),
                        LicenseTypeCode = site.Value.Field<string>("LicenseTypeCode"),
                        OpenDate = site.Value.Field<string>("OpenDate"),
                        CloseDate = site.Value.Field<string>("CloseDate"),
                        DirectorPrefixName = site.Value.Field<string>("DirectorPrefixName"),
                        DirectorFirstName = site.Value.Field<string>("DirectorFirstName"),
                        DirectorMiddleInitial = site.Value.Field<string>("DirectorMiddleInitial"),
                        DirectorLastName = site.Value.Field<string>("DirectorLastName"),
                        DirectorPhoneNumber = site.Value.Field<string>("DirectorPhoneNumber")
                    }).ToArray()
                }).ToArray();
    
                XmlWriterSettings settings = new XmlWriterSettings();
                settings.Indent = true;
                XmlWriter writer = XmlWriter.Create(FILENAME, settings);
                XmlSerializer serializer = new XmlSerializer(typeof(Providers));
                serializer.Serialize(writer,providers);
    
    
            }
        }
        //------------------------------------------------------------------------------
        // <auto-generated>
        //     This code was generated by a tool.
        //     Runtime Version:2.0.50727.6421
        //
        //     Changes to this file may cause incorrect behavior and will be lost if
        //     the code is regenerated.
        // </auto-generated>
        //------------------------------------------------------------------------------
    
    
    
        // 
        // This source code was auto-generated by xsd, Version=2.0.50727.3038.
        // 
    
    
        /// <remarks/>
        [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
        [System.SerializableAttribute()]
        [System.Diagnostics.DebuggerStepThroughAttribute()]
        [System.ComponentModel.DesignerCategoryAttribute("code")]
        [System.Xml.Serialization.XmlTypeAttribute(AnonymousType=true)]
        [System.Xml.Serialization.XmlRootAttribute(Namespace="", IsNullable=false)]
        public partial class Providers {
    
            private ProvidersProvider[] providerField;
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute("Provider", Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public ProvidersProvider[] Provider {
                get {
                    return this.providerField;
                }
                set {
                    this.providerField = value;
                }
            }
        }
    
        /// <remarks/>
        [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
        [System.SerializableAttribute()]
        [System.Diagnostics.DebuggerStepThroughAttribute()]
        [System.ComponentModel.DesignerCategoryAttribute("code")]
        [System.Xml.Serialization.XmlTypeAttribute(AnonymousType=true)]
        public partial class ProvidersProvider {
    
            private string federalTaxIdentifierField;
    
            private string providerNameField;
    
            private string contractualRelationshipCodeField;
    
            private ProvidersProviderProviderSite[] providerSitesField;
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string FederalTaxIdentifier {
                get {
                    return this.federalTaxIdentifierField;
                }
                set {
                    this.federalTaxIdentifierField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string ProviderName {
                get {
                    return this.providerNameField;
                }
                set {
                    this.providerNameField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string ContractualRelationshipCode {
                get {
                    return this.contractualRelationshipCodeField;
                }
                set {
                    this.contractualRelationshipCodeField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlArrayAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            [System.Xml.Serialization.XmlArrayItemAttribute("ProviderSite", Form=System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable=false)]
            public ProvidersProviderProviderSite[] ProviderSites {
                get {
                    return this.providerSitesField;
                }
                set {
                    this.providerSitesField = value;
                }
            }
        }
    
        /// <remarks/>
        [System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
        [System.SerializableAttribute()]
        [System.Diagnostics.DebuggerStepThroughAttribute()]
        [System.ComponentModel.DesignerCategoryAttribute("code")]
        [System.Xml.Serialization.XmlTypeAttribute(AnonymousType=true)]
        public partial class ProvidersProviderProviderSite {
    
            private string siteIdentifierField;
    
            private string siteNameField;
    
            private string licenseTypeCodeField;
    
            private string openDateField;
    
            private string closeDateField;
    
            private string directorPrefixNameField;
    
            private string directorFirstNameField;
    
            private string directorMiddleInitialField;
    
            private string directorLastNameField;
    
            private string directorPhoneNumberField;
    
            private string nationalProviderIdentifierField;
    
            private string webAddressField;
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string SiteIdentifier {
                get {
                    return this.siteIdentifierField;
                }
                set {
                    this.siteIdentifierField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string SiteName {
                get {
                    return this.siteNameField;
                }
                set {
                    this.siteNameField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string LicenseTypeCode {
                get {
                    return this.licenseTypeCodeField;
                }
                set {
                    this.licenseTypeCodeField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string OpenDate {
                get {
                    return this.openDateField;
                }
                set {
                    this.openDateField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string CloseDate {
                get {
                    return this.closeDateField;
                }
                set {
                    this.closeDateField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string DirectorPrefixName {
                get {
                    return this.directorPrefixNameField;
                }
                set {
                    this.directorPrefixNameField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string DirectorFirstName {
                get {
                    return this.directorFirstNameField;
                }
                set {
                    this.directorFirstNameField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string DirectorMiddleInitial {
                get {
                    return this.directorMiddleInitialField;
                }
                set {
                    this.directorMiddleInitialField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string DirectorLastName {
                get {
                    return this.directorLastNameField;
                }
                set {
                    this.directorLastNameField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string DirectorPhoneNumber {
                get {
                    return this.directorPhoneNumberField;
                }
                set {
                    this.directorPhoneNumberField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string NationalProviderIdentifier {
                get {
                    return this.nationalProviderIdentifierField;
                }
                set {
                    this.nationalProviderIdentifierField = value;
                }
            }
    
            /// <remarks/>
            [System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
            public string WebAddress {
                get {
                    return this.webAddressField;
                }
                set {
                    this.webAddressField = value;
                }
            }
        }
    
    }
    

    我用了以下xsd

    <?xml version="1.0" encoding="utf-8" ?>
    <schema xmlns="http://www.w3.org/2001/XMLSchema" xmlns:xs="http://www.w3.org/2001/XMLSchema">
      <xs:element name="Providers">
        <xs:complexType>
          <xs:sequence>
            <xs:element maxOccurs="unbounded" name="Provider">
              <xs:complexType>
                <xs:all>
                  <xs:element minOccurs="0" name="FederalTaxIdentifier" type="xs:string" />
                  <xs:element minOccurs="0" name="ProviderName" type="xs:string" />
                  <xs:element minOccurs="0" name="ContractualRelationshipCode" type="xs:string" />
                  <xs:element minOccurs="0" name="ProviderSites">
                    <xs:complexType>
                      <xs:sequence>
                        <xs:element maxOccurs="unbounded" name="ProviderSite">
                          <xs:complexType>
                            <xs:all>
                              <xs:element minOccurs="0" name="SiteIdentifier" type="xs:string" />
                              <xs:element minOccurs="0" name="SiteName" type="xs:string" />
                              <xs:element minOccurs="0" name="LicenseTypeCode" type="xs:string" />
                              <xs:element minOccurs="0" name="OpenDate" type="xs:string" />
                              <xs:element minOccurs="0" name="CloseDate" type="xs:string" />
                              <xs:element minOccurs="0" name="DirectorPrefixName" type="xs:string" />
                              <xs:element minOccurs="0" name="DirectorFirstName" type="xs:string" />
                              <xs:element minOccurs="0" name="DirectorMiddleInitial" type="xs:string" />
                              <xs:element minOccurs="0" name="DirectorLastName" type="xs:string" />
                              <xs:element minOccurs="0" name="DirectorPhoneNumber" type="xs:string" />
                              <xs:element minOccurs="0" name="NationalProviderIdentifier" type="xs:string" />
                              <xs:element minOccurs="0" name="WebAddress" type="xs:string" />
                            </xs:all>
                          </xs:complexType>
                        </xs:element>
                      </xs:sequence>
                    </xs:complexType>
                  </xs:element>
                </xs:all>
              </xs:complexType>
            </xs:element>
          </xs:sequence>
        </xs:complexType>
      </xs:element>
      </schema>
    

    【讨论】:

    • 这工作谢谢!我试图为“ProviderSiteLicenseIdentifiers”创建一个数组,就像您为“ProviderSites”所做的那样,它说“ProvidersProvider 不包含 ProviderSiteLicenseIdentifiers 的定义”,我错过了什么?
    • 我刚刚使用 xsd.exe 工具从您提供的 xsd 生成类。
    • 我想通了,我忘记了“ProviderSiteLicenseIdentifiers”是“ProviderSites”的子元素再次感谢!
    • 试图弄清楚如何添加一个元素两次,比如一个导演有 2 个不同的电话号码或有 2 个不同的网址。
    • 您需要表格中的其他列和新元素。拥有三个电话号码 Home、Work、Cell。您可以使用列表。请参阅:msdn.microsoft.com/en-us/library/ms256162(v=vs.110).aspx
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-12-07
    • 1970-01-01
    • 1970-01-01
    • 2013-05-09
    • 1970-01-01
    相关资源
    最近更新 更多