Xslt 为嵌套XML生成XSL(非规范化格式)

Xslt 为嵌套XML生成XSL(非规范化格式),xslt,xml-parsing,flatten,Xslt,Xml Parsing,Flatten,我需要将我的XML展平,因为文件大小非常大并且是嵌套级别的,我正在手动创建XSL文件。下面是XML文件内容的示例场景- <StudentDetail> <SchoolName>SSHPS</SchoolName> <SchoolEstablishedYear>1990</SchoolEstablishedYear> <ClassDetails> <ClassDetail> <

我需要将我的XML展平,因为文件大小非常大并且是嵌套级别的,我正在手动创建XSL文件。下面是XML文件内容的示例场景-

<StudentDetail>
  <SchoolName>SSHPS</SchoolName>
  <SchoolEstablishedYear>1990</SchoolEstablishedYear>
  <ClassDetails>
    <ClassDetail>
      <ClassStartedYear>1990</ClassStartedYear>
      <Section ID="12345">
        <SectioName>Section A</SectioName>
        <Students>
          <Student ID="1">
            <StudentName>John</StudentName>
            <Address>
              <HomeNumber>10</HomeNumber>
              <StreetName>Avenue</StreetName>
            </Address>
          </Student>
          <Student ID="2">
            <StudentName>Steve</StudentName>
          </Student>
        </Students>
      </Section>
      <Section ID="123456">
        <SectioName>Section B</SectioName>
        <Students>
          <Student ID="100">
            <StudentName>Dia</StudentName>
            <Age>6</Age>
          </Student>
          <Student ID="101">
            <StudentName>Kevin</StudentName>
          </Student>
        </Students>
      </Section>
    </ClassDetail>
    <ClassDetail>
      <ClassStartedYear>1995</ClassStartedYear>
      <Section ID="543466">
        <SectioName>Section A</SectioName>
        <Students>
          <Student ID="200">
            <StudentName>Dia</StudentName>
            <Muncipality>
              <AreaCode>100</AreaCode>
              <Areaname>GRAND</Areaname>
            </Muncipality>
          </Student>
          <Student ID="201">
            <StudentName>Liva</StudentName>
          </Student>
        </Students>
      </Section>
      <Section ID="7543466">
        <SectioName>Section A</SectioName>
        <Students>
          <Student ID="300">
            <StudentName>Zane</StudentName>
          </Student>
          <Student ID="301">
            <StudentName>Susan</StudentName>
          </Student>
        </Students>
      </Section>
    </ClassDetail>
  </ClassDetails>
</StudentDetail>

SSHPS
1990
1990
A节
约翰
10
大街
史蒂夫
B节
迪亚
6.
凯文
1995
A节
迪亚
100
宏伟的
利瓦
A节
赞恩
苏珊
以下是所需的XML格式-

<StudentDetail>
    <Student>
        <SchoolName>SSHPS</SchoolName>
        <SchoolEstablishedYear>1990</SchoolEstablishedYear>
        <ClassStartedYear>1990</ClassStartedYear>
        <SectionID>12345</SectionID>
        <SectioName>Section A</SectioName>
        <StudentID>1</StudentID>
        <StudentName>John</StudentName>
        <Address_HomeNumber>10</Address_HomeNumber>
        <Address_StreetName>Avenue</Address_StreetName>
        <Age> </Age>
        <Muncipality_AreaCode></Muncipality_AreaCode>
        <Muncipality_Areaname></Muncipality_Areaname>
    </Student>
   .
   .
   .
    <Student>
        <SchoolName>SSHPS</SchoolName>
        <SchoolEstablishedYear>1990</SchoolEstablishedYear>
        <ClassStartedYear>1995</ClassStartedYear>
        <SectionID>7543466</SectionID>
        <SectioName>Section A</SectioName>
        <StudentID>100</StudentID>
        <StudentName>Dia</StudentName>
        <Address_HomeNumber></Address_HomeNumber>
        <Address_StreetName></Address_StreetName>
        <Age></Age>
        <Muncipality_AreaCode>100</Muncipality_AreaCode>
        <Muncipality_Areaname>GRAND</Muncipality_Areaname>
    </Student>
</StudentDetail>

SSHPS
1990
1990
12345
A节
1.
约翰
10
大街
.
.
.
SSHPS
1990
1995
7543466
A节
100
迪亚
100
宏伟的
我已经生成了XSL模板,我无法加载它,因为其中有一些错误-

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output indent="yes" method="xml"/>
<xsl:template match="/">
    <StudentDetail>
        <xsl:for-each select="StudentDetail/ClassDetails">
         <Student>
            <SchoolName><xsl:value-of select="StudentDetail/SchoolName"/></SchoolName>
            <SchoolEstablishedYear><xsl:value-of select="StudentDetail/SchoolEstablishedYear"/></SchoolEstablishedYear>
            <ClassStartedYear><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/ClassStartedYear"/></ClassStartedYear>
            <StudentID><xsl:value-of select="StudentDetail/ClassDetails/Section/@ID"/></StudentID>
            <SectioName><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/Section/SectionName"/></SectioName>
            <StudentID><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/Section/Students/Student/@ID"/></StudentID>
            <StudentName><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/Section/Students/Student"/></StudentName>
            <Address_HomeNumber><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/Section/Students/Student/Address/HomeNumber"/></Address_HomeNumber>
            <Address_StreetName><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/Section/Students/Student/Address/StreetName"/></Address_StreetName>
            <Age><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/Section/Students/Student/Age"/></Age>
            <Muncipality_AreaCode><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/Section/Students/Student/Muncipality/AreaCode"/></Muncipality_AreaCode>
            <Muncipality_Areaname><xsl:value-of select="StudentDetail/ClassDetails/ClassDetail/Section/Students/Student/Muncipality/Areaname"/></Muncipality_Areaname>
         </Student>
        </xsl:for-each>
    </StudentDetail>       
</xsl:template>



我不熟悉处理XML,我一直在处理嵌套的XML。首先,我很惊讶有人会想把这个结构良好的输入转换成结构不良的输出。但我们不是来讨论这个的

其次,我对“手动生成XSL”的说法感到困惑。我本以为您是手动创建的,或者是以编程方式生成的,现在还不清楚哪种情况是这样

第三,您已经告诉我们生成的XSL中存在“一些错误”,但您没有告诉我们该错误是什么。我能看到的唯一错误是
xsl:stylesheet
元素缺少一个close标记,这可能是一个打字错误。如果您遇到错误,请告诉我们错误是什么

第四,似乎有一种更简单的方法。就我所见,您可以通过应用三个规则来实现所需的输出:

  • 如果一个元素有子元素,只处理它的子元素

  • 如果元素具有ID属性,请将
    更改为
    x
    ,然后处理其子元素

  • 如果元素具有文本节点子元素,则复制它时不作更改

第一个规则对应于缺省XSLT处理规则;其他两条规则可以简单地在XSLT中扩展为:

<xsl:template match="*[@ID]">
  <xsl:element name="{name()}ID">
    <xsl:value-of select="@ID"/>
  </xsl:element>
  <xsl:apply-templates/>
</xsl:template>

<xsl:template match="*[text()]">
  <xsl:copy-of select="."/>
</xsl:template>

首先,我很惊讶有人会想把这种结构良好的输入转换成结构不良的输出。但我们不是来讨论这个的

其次,我对“手动生成XSL”的说法感到困惑。我本以为您是手动创建的,或者是以编程方式生成的,现在还不清楚哪种情况是这样

第三,您已经告诉我们生成的XSL中存在“一些错误”,但您没有告诉我们该错误是什么。我能看到的唯一错误是
xsl:stylesheet
元素缺少一个close标记,这可能是一个打字错误。如果您遇到错误,请告诉我们错误是什么

第四,似乎有一种更简单的方法。就我所见,您可以通过应用三个规则来实现所需的输出:

  • 如果一个元素有子元素,只处理它的子元素

  • 如果元素具有ID属性,请将
    更改为
    x
    ,然后处理其子元素

  • 如果元素具有文本节点子元素,则复制它时不作更改

第一个规则对应于缺省XSLT处理规则;其他两条规则可以简单地在XSLT中扩展为:

<xsl:template match="*[@ID]">
  <xsl:element name="{name()}ID">
    <xsl:value-of select="@ID"/>
  </xsl:element>
  <xsl:apply-templates/>
</xsl:template>

<xsl:template match="*[text()]">
  <xsl:copy-of select="."/>
</xsl:template>

样式表的主要问题是,您为每个
类详细信息
创建了一个
学生
,而不是为每个
学生

而不是:

<xsl:for-each select="StudentDetail/ClassDetails">
    <Student>
        <!-- data -->
    </Student>
</xsl:for-each>

样式表的主要问题是,您正在为每个
ClassDetails
而不是为每个
Student
创建一个
Student

而不是:

<xsl:for-each select="StudentDetail/ClassDetails">
    <Student>
        <!-- data -->
    </Student>
</xsl:for-each>

1.您的输入有8名学生,您的预期输出仅显示2名学生。为什么?--2.我看到同一个学生出现在多个班级的可能性;那该怎么办?谢谢。我更新了问题。我重新创建了一个与我面临的问题类似的场景。我想列出所有的8名学生。为了便于解释,我考虑过一个班级会有多个部分,每个部分都会有一组学生。你还没有回答我的第二个问题。好的,为了回答第二个问题,同一个学生不会出现在多个班级,这是我的假设1。您的输入有8名学生,您的预期输出仅显示2名学生。为什么?--2.我看到同一个学生出现在多个班级的可能性;那该怎么办?谢谢。我更新了问题。我重新创建了一个与我面临的问题类似的场景。我想列出所有的8名学生。为了解释的目的,我考虑过一个班级会有多个部分,每个部分会有一组学生。你没有回答我的第二个问题。好的,为了回答第二个问题,同一个学生不会出现在多个班级,这是我的假设