我有一个嵌套子级3-4级的XML文件。有些孩子有一个缺少的元素或一个额外的元素。我很努力地自动读取xml x children并且创建相应的平分隔记录以匹配父项目。我在一个winform应用程序中使用VS 2015和C#,并且文件的最终结果是它们的记录结构需要对所有项目都是相同的,而不管缺少或空白的元素。下面是我的按钮点击事件以及我正在处理的数据样本。注意ITEM 1有1个分区节点,ITEM 2有2个分区节点,ITEM 3有0个分区节点。例如,当我将它带入EXCEL时,结果会在分隔文件中抛出我的列Counts。在没有XSLT文件的情况下阅读C#中的嵌套XML
private void button1_Click(object sender, EventArgs e)
{
try
{
string sDelimiter = "";
string sNodeName = "";
string sChildNodeName = "";
switch (uicmbDelimiter.Text)
{
case "TAB":
sDelimiter = "\t";
break;
case "PIPE":
sDelimiter = "|";
break;
case "COMMA":
sDelimiter = ",";
break;
default:
sDelimiter = ",";
break;
}
string csvstring = "";
StreamWriter csv = new StreamWriter(this.uitxtXMLFile.Text + ".out");
XmlDocument doc = new XmlDocument();
doc.Load(this.uitxtXMLFile.Text);
XmlNamespaceManager nsmgr = new XmlNamespaceManager(doc.NameTable);
nsmgr.AddNamespace("ab", "http://www.revenue.wi.gov/slf");
XmlNodeList nodelist = doc.SelectNodes("//ab:Item", nsmgr);
foreach (XmlNode xnfields in nodelist)
{
foreach (XmlNode childnode in xnfields.ChildNodes)
{
if (childnode.ChildNodes.Count > 1)
{
foreach (XmlNode children in childnode.ChildNodes)
{
csvstring +=children.LocalName + sDelimiter;
}
}
else
{
csvstring += childnode.LocalName + sDelimiter;
}
}
csv.WriteLine(csvstring);
csvstring = "";
break;
}
csvstring = "";
foreach (XmlNode xn in nodelist)
{
foreach (XmlNode childnode in xn.ChildNodes)
{
if (childnode.ChildNodes.Count > 1)
{
foreach (XmlNode children in childnode.ChildNodes)
{
if ((sChildNodeName != children.LocalName) && sChildNodeName !="")
{
csvstring += sDelimiter + children.InnerText;
}
else
{
csvstring += children.InnerText;
}
sChildNodeName = children.LocalName;
}
}
else
{
csvstring += childnode.InnerText;
}
///////////
///
///////////
if ((sNodeName != childnode.LocalName))
{
csvstring += sDelimiter;
}
sNodeName = childnode.LocalName;
}
csv.WriteLine(csvstring);
csvstring = "";
sNodeName = "";
sChildNodeName = "";
}
csv.Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.InnerException.Message);
}
}
<?xml version="1.0" encoding="utf-8"?>
<CountyRolls xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://www.revenue.wi.gov/slf">
<Municipality>
<MunicipalityNumber>002</MunicipalityNumber>
<Item>
<RecordNumber>1</RecordNumber>
<PropertyInfo>
<LocalID1>1-00001-000</LocalID1>
<LocalID2>1</LocalID2>
<Zoning>EXCLUSIVE AGRICULTURE DISTRICT</Zoning>
<Town>16</Town>
<Range>05</Range>
<RangeDirection>W</RangeDirection>
<Section>01</Section>
<Quarter40>NE</Quarter40>
<Quarter160>NE</Quarter160>
<Legal>FRAC NE1/4 OF NE1/4</Legal>
<RecordingDocuments>
<Book>0</Book>
<Page>0</Page>
<DocumentNumber>1569517</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>589</Book>
<Page>204</Page>
<DocumentNumber>868152</DocumentNumber>
</RecordingDocuments>
</PropertyInfo>
<OwnerAndAddressInfo>
<MailingAddress>
<USAddress>
<AddressLine1>N4929 COUNTY ROAD J</AddressLine1>
<City>ROCKLAND</City>
<State>WI</State>
<ZIPCode>54653</ZIPCode>
</USAddress>
</MailingAddress>
<Owner>
<Individual>
<Name>
<FirstName>DAVID</FirstName>
<LastName>AXELSEN IRREVOCABLE LIVING TRUST</LastName>
</Name>
<Address>
<USAddress>
<AddressLine1>N4929 COUNTY ROAD J</AddressLine1>
<City>ROCKLAND</City>
<State>WI</State>
<ZIPCode>54653</ZIPCode>
</USAddress>
</Address>
</Individual>
</Owner>
<Owner>
<Individual>
<Name>
<FirstName>RHEA</FirstName>
<LastName>AXELSEN IRREVOCABLE LIVING TRUST</LastName>
</Name>
<Address>
<USAddress>
<AddressLine1>N4929 COUNTY ROAD J</AddressLine1>
<City>ROCKLAND</City>
<State>WI</State>
<ZIPCode>54653</ZIPCode>
</USAddress>
</Address>
</Individual>
</Owner>
<SiteAddress>
<AddressLine1>JACKPOT AVE</AddressLine1>
<City>ROCKLAND</City>
<State>WI</State>
<ZIPCode>54653</ZIPCode>
</SiteAddress>
</OwnerAndAddressInfo>
<ValuationInfo>
<RealProperty>
<Class4>
<Acres>8.000</Acres>
<LandValue>1200</LandValue>
<ImprovementsValue>0</ImprovementsValue>
</Class4>
<Class5M>
<Acres>31.460</Acres>
<LandValue>50300</LandValue>
<ImprovementsValue>0</ImprovementsValue>
</Class5M>
<ClassTotal>
<Acres>39.460</Acres>
<LandValue>51500</LandValue>
<ImprovementsValue>0</ImprovementsValue>
</ClassTotal>
</RealProperty>
</ValuationInfo>
<JurisdictionInfo>
<County>
<CountyName>32 La Crosse</CountyName>
<CountyRate>0.004068228</CountyRate>
<CountyTax>209.51</CountyTax>
</County>
<Municipality>
<MuniName>Town of Bangor</MuniName>
<MuniNumber>32002</MuniNumber>
<MunicipalRate>0.002443039</MunicipalRate>
<MunicipalTax>125.82</MunicipalTax>
</Municipality>
<School>
<Code>320245</Code>
<Rate>0.009154910</Rate>
<Tax>471.48</Tax>
</School>
<Tech>
<Code>000200</Code>
<Rate>0.001590738</Rate>
<Tax>81.92</Tax>
</Tech>
</JurisdictionInfo>
<TaxSummary>
<LandTaxableTotal>51500</LandTaxableTotal>
<ImprovementsTaxableTotal>0</ImprovementsTaxableTotal>
<TotalTaxableValue>51500</TotalTaxableValue>
<EstimatedFairMarketValue>0</EstimatedFairMarketValue>
<StateTax>8.86</StateTax>
<OccupationalTax>0</OccupationalTax>
<ForestTaxable>0</ForestTaxable>
<BORValue>51500</BORValue>
<PrivateForestCropTax>0.00</PrivateForestCropTax>
<ManagedForestLawTax>0.00</ManagedForestLawTax>
<TaxTotal>897.59</TaxTotal>
<SchoolCredit>95.43</SchoolCredit>
<LotteryCredit>0.00</LotteryCredit>
<FirstDollarCredit>0.00</FirstDollarCredit>
<SpecialAssessment>
<SpecialAssessmentDesc>No special charge applies to parcel.</SpecialAssessmentDesc>
<SpecialAssessmentCharge>0</SpecialAssessmentCharge>
</SpecialAssessment>
<DelinquentUtilityCharges>0</DelinquentUtilityCharges>
<NetTax>897.59</NetTax>
<Payment>0</Payment>
<AmountDue>897.59</AmountDue>
<PriorYearChargebacks>
<Total>0</Total>
</PriorYearChargebacks>
<StateAssessedTelco>0</StateAssessedTelco>
</TaxSummary>
</Item>
<Item>
<RecordNumber>2</RecordNumber>
<PropertyInfo>
<LocalID1>1-00003-001</LocalID1>
<LocalID2>4</LocalID2>
<Zoning>CONDITIONAL ZONING </Zoning>
<Zoning>EXCLUSIVE AGRICULTURE DISTRICT</Zoning>
<Town>16</Town>
<Range>05</Range>
<RangeDirection>W</RangeDirection>
<Section>01</Section>
<Quarter40>NE</Quarter40>
<Quarter160>SW</Quarter160>
<Legal>CERTIFIED SURVEY MAP NO. 64 VOL 7 LOT 1 DOC NO. 1159544</Legal>
<RecordingDocuments>
<Book>7</Book>
<Page>64</Page>
<DocumentNumber>1159544</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>872</Book>
<Page>36</Page>
<DocumentNumber>1039008</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>1129</Book>
<Page>264</Page>
<DocumentNumber>1152228</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>1140</Book>
<Page>558</Page>
<DocumentNumber>1156940</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>1156</Book>
<Page>31</Page>
<DocumentNumber>1163596</DocumentNumber>
</RecordingDocuments>
</PropertyInfo>
<OwnerAndAddressInfo>
<MailingAddress>
<USAddress>
<AddressLine1>N4746 COUNTY ROAD J</AddressLine1>
<City>ROCKLAND</City>
<State>WI</State>
<ZIPCode>54653</ZIPCode>
</USAddress>
</MailingAddress>
<Owner>
<Individual>
<Name>
<FirstName>SCOTT R</FirstName>
<LastName>MILDE</LastName>
</Name>
<Address>
<USAddress>
<AddressLine1>N4746 COUNTY ROAD J</AddressLine1>
<City>ROCKLAND</City>
<State>WI</State>
<ZIPCode>54653</ZIPCode>
</USAddress>
</Address>
</Individual>
</Owner>
<Owner>
<Individual>
<Name>
<FirstName>SUSAN T</FirstName>
<LastName>MILDE</LastName>
</Name>
</Individual>
</Owner>
<SiteAddress>
<AddressLine1>N4746 COUNTY ROAD J</AddressLine1>
<City>ROCKLAND</City>
<State>WI</State>
<ZIPCode>54653</ZIPCode>
</SiteAddress>
</OwnerAndAddressInfo>
<ValuationInfo>
<RealProperty>
<Class1>
<Acres>1.760</Acres>
<LandValue>13800</LandValue>
<ImprovementsValue>127400</ImprovementsValue>
</Class1>
<ClassTotal>
<Acres>1.760</Acres>
<LandValue>13800</LandValue>
<ImprovementsValue>127400</ImprovementsValue>
</ClassTotal>
</RealProperty>
</ValuationInfo>
<JurisdictionInfo>
<County>
<CountyName>32 La Crosse</CountyName>
<CountyRate>0.004068228</CountyRate>
<CountyTax>574.43</CountyTax>
</County>
<Municipality>
<MuniName>Town of Bangor</MuniName>
<MuniNumber>32002</MuniNumber>
<MunicipalRate>0.002443039</MunicipalRate>
<MunicipalTax>344.96</MunicipalTax>
</Municipality>
<School>
<Code>320245</Code>
<Rate>0.009154910</Rate>
<Tax>1292.67</Tax>
</School>
<Tech>
<Code>000200</Code>
<Rate>0.001590738</Rate>
<Tax>224.61</Tax>
</Tech>
</JurisdictionInfo>
<TaxSummary>
<LandTaxableTotal>13800</LandTaxableTotal>
<ImprovementsTaxableTotal>127400</ImprovementsTaxableTotal>
<TotalTaxableValue>141200</TotalTaxableValue>
<EstimatedFairMarketValue>143200</EstimatedFairMarketValue>
<StateTax>24.30</StateTax>
<OccupationalTax>0</OccupationalTax>
<ForestTaxable>0</ForestTaxable>
<BORValue>141200</BORValue>
<PrivateForestCropTax>0.00</PrivateForestCropTax>
<ManagedForestLawTax>0.00</ManagedForestLawTax>
<TaxTotal>2460.97</TaxTotal>
<SchoolCredit>261.64</SchoolCredit>
<LotteryCredit>136.65</LotteryCredit>
<FirstDollarCredit>72.66</FirstDollarCredit>
<SpecialAssessment>
<SpecialAssessmentDesc>No special charge applies to parcel.</SpecialAssessmentDesc>
<SpecialAssessmentCharge>0</SpecialAssessmentCharge>
</SpecialAssessment>
<DelinquentUtilityCharges>0</DelinquentUtilityCharges>
<NetTax>2251.66</NetTax>
<Payment>0</Payment>
<AmountDue>2251.66</AmountDue>
<PriorYearChargebacks>
<Total>0</Total>
</PriorYearChargebacks>
<StateAssessedTelco>0</StateAssessedTelco>
</TaxSummary>
</Item>
<Item>
<RecordNumber>3</RecordNumber>
<PropertyInfo>
<LocalID1>1-00004-000</LocalID1>
<LocalID2>5</LocalID2>
<Town>16</Town>
<Range>05</Range>
<RangeDirection>W</RangeDirection>
<Section>01</Section>
<Quarter40>NE</Quarter40>
<Quarter160>SE</Quarter160>
<Legal>SE1/4 FRAC NE1/4</Legal>
<RecordingDocuments>
<Book>870</Book>
<Page>575</Page>
<DocumentNumber>1038082</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>872</Book>
<Page>36</Page>
<DocumentNumber>1039008</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>1129</Book>
<Page>264</Page>
<DocumentNumber>1152228</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>1140</Book>
<Page>558</Page>
<DocumentNumber>1156940</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>1336</Book>
<Page>55</Page>
<DocumentNumber>1234542</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>1336</Book>
<Page>523</Page>
<DocumentNumber>1234736</DocumentNumber>
</RecordingDocuments>
<RecordingDocuments>
<Book>1385</Book>
<Page>535</Page>
<DocumentNumber>1254119</DocumentNumber>
</RecordingDocuments>
</PropertyInfo>
<OwnerAndAddressInfo>
<MailingAddress>
<USAddress>
<AddressLine1>230 21ST ST S</AddressLine1>
<City>LA CROSSE</City>
<State>WI</State>
<ZIPCode>54601</ZIPCode>
</USAddress>
</MailingAddress>
<Owner>
<Individual>
<Name>
<FirstName>GALEN W</FirstName>
<LastName>PITTMAN</LastName>
</Name>
<Address>
<USAddress>
<AddressLine1>230 21ST ST S</AddressLine1>
<City>LA CROSSE</City>
<State>WI</State>
<ZIPCode>54601</ZIPCode>
</USAddress>
</Address>
</Individual>
</Owner>
<SiteAddress>
<AddressLine1>COUNTY ROAD J</AddressLine1>
<City>ROCKLAND</City>
<State>WI</State>
<ZIPCode>54653</ZIPCode>
</SiteAddress>
</OwnerAndAddressInfo>
<ValuationInfo>
<RealProperty>
<Class5>
<Acres>9.000</Acres>
<LandValue>11700</LandValue>
<ImprovementsValue>0</ImprovementsValue>
</Class5>
<Class6>
<Acres>31.000</Acres>
<LandValue>99200</LandValue>
<ImprovementsValue>0</ImprovementsValue>
</Class6>
<ClassTotal>
<Acres>40.000</Acres>
<LandValue>110900</LandValue>
<ImprovementsValue>0</ImprovementsValue>
</ClassTotal>
</RealProperty>
</ValuationInfo>
<JurisdictionInfo>
<County>
<CountyName>32 La Crosse</CountyName>
<CountyRate>0.004068228</CountyRate>
<CountyTax>451.17</CountyTax>
</County>
<Municipality>
<MuniName>Town of Bangor</MuniName>
<MuniNumber>32002</MuniNumber>
<MunicipalRate>0.002443039</MunicipalRate>
<MunicipalTax>270.93</MunicipalTax>
</Municipality>
<School>
<Code>320245</Code>
<Rate>0.009154910</Rate>
<Tax>1015.28</Tax>
</School>
<Tech>
<Code>000200</Code>
<Rate>0.001590738</Rate>
<Tax>176.41</Tax>
</Tech>
</JurisdictionInfo>
<TaxSummary>
<LandTaxableTotal>110900</LandTaxableTotal>
<ImprovementsTaxableTotal>0</ImprovementsTaxableTotal>
<TotalTaxableValue>110900</TotalTaxableValue>
<EstimatedFairMarketValue>112500</EstimatedFairMarketValue>
<StateTax>19.09</StateTax>
<OccupationalTax>0</OccupationalTax>
<ForestTaxable>0</ForestTaxable>
<BORValue>110900</BORValue>
<PrivateForestCropTax>0.00</PrivateForestCropTax>
<ManagedForestLawTax>0.00</ManagedForestLawTax>
<TaxTotal>1932.88</TaxTotal>
<SchoolCredit>205.50</SchoolCredit>
<LotteryCredit>0.00</LotteryCredit>
<FirstDollarCredit>0.00</FirstDollarCredit>
<SpecialAssessment>
<SpecialAssessmentDesc>No special charge applies to parcel.</SpecialAssessmentDesc>
<SpecialAssessmentCharge>0</SpecialAssessmentCharge>
</SpecialAssessment>
<DelinquentUtilityCharges>0</DelinquentUtilityCharges>
<NetTax>1932.88</NetTax>
<Payment>0</Payment>
<AmountDue>1932.88</AmountDue>
<PriorYearChargebacks>
<Total>0</Total>
</PriorYearChargebacks>
<StateAssessedTelco>0</StateAssessedTelco>
</TaxSummary>
</Item>
<Chargebacks>
<CurrentYear>
<Total>0</Total>
</CurrentYear>
</Chargebacks>
</Municipality>
</CountyRolls>
我的XML复制到剪贴板,并使用VS“粘贴XML作为类”功能。然后在该类中实现一个方法,将它写出为分隔字符串。然后你可以使用XmlSerializer。 – Crowcoder