首页 > 解决方案 > 如何计算和评估 XML 中的节点以在 HTML 表中创建行跨度值?

问题描述

我有一个 xml 文档。我有一些节点。1.Management(有一些Upravlinnya),2.Upravlinnya(有一些viddils)和viddils(就像部门)包含一些工人我解决了我的问题,因为你只能用viddils看到。但我实际上不知道为什么它不能与其他人一起工作。我的表输出(现在):

应该 怎样 应该怎样 My Xslt 文件

<?xml version="1.0"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="/">
  <html>
  <body>
    <h2>Labka -7 Kondera Sviatoslav</h2>
    <table border="1">
      <tr bgcolor="#9acd32">
        <th>Management Name</th>
        <th>Upravlinnya Name</th>
        <th>Viddil Name</th>
        <th>Name</th>
        <th>Surname</th>
        <th>Birth Year</th>
      </tr>
      <xsl:for-each select="Managements/Management">
        <xsl:for-each select="Upravlinnyas/Upravlinnya">
          <xsl:for-each select="Viddils/Viddil">
            <xsl:for-each select="Workers/Worker">
              <tr>
                 <xsl:if test="position() = 1">
                 <td rowspan="{last()}"> 
                  <xsl:value-of select="ancestor::Management[1]/ManagementName"/>
                 </td>
                 </xsl:if>
                 <xsl:if test="position() = 1">
                 <td rowspan="{last()}"> 
                  <xsl:value-of select="ancestor::Upravlinnya[1]/UpravlinnyaName"/>
                 </td>
                 </xsl:if>
                   <xsl:if test="position() = 1">
                     <td rowspan="{last()}"> 
                     <xsl:value-of select="ancestor::Viddil[1]/ViddilName"/> 
                   </td>
                 </xsl:if>
                  <td><xsl:value-of select="WorkerName"/></td>
                  <td><xsl:value-of select="WorkerSurname"/></td>
                  <td><xsl:value-of select="BirthYear"/></td>
             </tr>    
            </xsl:for-each>  
                      
          </xsl:for-each>           
      </xsl:for-each>      
     </xsl:for-each>
    </table>
  </body>
  </html>
</xsl:template>
</xsl:stylesheet>

还有我的 xml 文档(我的文档的一部分)

<?xml-stylesheet type = "text/xsl" href = "labka.xsl"?>
<Managements>
  <Management id="1111">
    <ManagementName>Management_1</ManagementName>
    <Upravlinnyas>
      <Upravlinnya id="1111">
        <UpravlinnyaName>Upravlinnya_1</UpravlinnyaName>
        <Viddils>
          <Viddil id ="1111">
            <ViddilName>Viddil_1</ViddilName>
            <Workers>
              <Worker id="1111">
                <WorkerName>Sviatoslav</WorkerName>
                <WorkerSurname>Kondera</WorkerSurname>
                <BirthYear>2002</BirthYear>
              </Worker>
              <Worker id="2222">
                <WorkerName>Orest</WorkerName>
                <WorkerSurname>Rodcevich</WorkerSurname>
                <BirthYear>1999</BirthYear>
              </Worker>
              <Worker id="3333">
                <WorkerName>Olena</WorkerName>
                <WorkerSurname>Zelenska</WorkerSurname>
                <BirthYear>1978</BirthYear>
              </Worker>
            </Workers>
          </Viddil>
          <Viddil id ="7777">
            <ViddilName>Viddil_17</ViddilName>
            <Workers>
              <Worker id="1111">
                <WorkerName>SviatoslavNew</WorkerName>
                <WorkerSurname>KonderaNew</WorkerSurname>
                <BirthYear>2012</BirthYear>
              </Worker>
            </Workers>
          </Viddil>
        </Viddils>
      </Upravlinnya>
    </Upravlinnyas>
  </Management>
  <Management id="2222">
    <ManagementName>Management_2</ManagementName>
    <Upravlinnyas>
      <Upravlinnya id="2222">
        <UpravlinnyaName>Upravlinnya_2</UpravlinnyaName>
        <Viddils>
          <Viddil id ="2222">
            <ViddilName>Viddil_2</ViddilName>
            <Workers>
              <Worker id="4444">
                <WorkerName>Nidia</WorkerName>
                <WorkerSurname>Dorofeeva</WorkerSurname>
                <BirthYear>2016</BirthYear>
              </Worker>
              <Worker id="5555">
                <WorkerName>Petro</WorkerName>
                <WorkerSurname>Poroshenko</WorkerSurname>
                <BirthYear>1976</BirthYear>
              </Worker>
            </Workers>
          </Viddil>
        </Viddils>
      </Upravlinnya>
    </Upravlinnyas>
  </Management>
  <Management id="3333">
    <ManagementName>Management_333</ManagementName>
    <Upravlinnyas>
      <Upravlinnya id="3333">
        <UpravlinnyaName>Upravlinnya_222</UpravlinnyaName>
        <Viddils>
          <Viddil id ="3333">
            <ViddilName>Viddil_222</ViddilName>
            <Workers>
              <Worker id="6666">
                <WorkerName>Marsha</WorkerName>
                <WorkerSurname>May</WorkerSurname>
                <BirthYear>1995</BirthYear>
              </Worker>
            </Workers>
          </Viddil>
          <Viddil id ="9999">
            <ViddilName>Viddil_212</ViddilName>
            <Workers>
              <Worker id="1010">
                <WorkerName>MarshaNew</WorkerName>
                <WorkerSurname>MayNew</WorkerSurname>
                <BirthYear>1905</BirthYear>
              </Worker>
            </Workers>
          </Viddil>
        </Viddils>
      </Upravlinnya>
    </Upravlinnyas>
  </Management>
</Managements>

感谢您的帮助)我期待您的解决方案!)我觉得只需要更改几行

标签: xmlxslthtml-tablexslt-1.0xslt-2.0

解决方案


试试这种方式:

XSLT 1.0

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>

<xsl:template match="/Managements">
    <html>
        <body>
            <table border="1">
                <tr>
                    <th>Management Name</th>
                    <th>Upravlinnya Name</th>
                    <th>Viddil Name</th>
                    <th>Name</th>
                    <th>Surname</th>
                    <th>Birth Year</th>
                </tr>
                <xsl:apply-templates select="Management"/>
            </table>
        </body>
    </html>
</xsl:template> 

<xsl:template match="Management">
    <tr>
        <td rowspan="{count(Upravlinnyas/Upravlinnya) + count(Upravlinnyas/Upravlinnya/Viddils/Viddil) + count(Upravlinnyas/Upravlinnya/Viddils/Viddil/Workers/Worker) + 1}">
            <xsl:value-of select="ManagementName"/>
        </td>   
    </tr>
    <xsl:apply-templates select="Upravlinnyas/Upravlinnya"/>
</xsl:template> 

<xsl:template match="Upravlinnya">
    <tr>
        <td rowspan="{count(Viddils/Viddil) + count(Viddils/Viddil/Workers/Worker) + 1}">
            <xsl:value-of select="UpravlinnyaName"/>
        </td>   
    </tr>
    <xsl:apply-templates select="Viddils/Viddil"/>
</xsl:template> 

<xsl:template match="Viddil">
    <tr>
        <td rowspan="{count(Workers/Worker) + 1}">
            <xsl:value-of select="ViddilName"/>
        </td>   
    </tr>
    <xsl:apply-templates select="Workers/Worker"/>
</xsl:template> 

<xsl:template match="Worker">
    <tr>
        <td>
            <xsl:value-of select="WorkerName"/>
        </td>
        <td>
            <xsl:value-of select="WorkerSurname"/>
        </td>
        <td>
            <xsl:value-of select="BirthYear"/>
        </td>
    </tr>
</xsl:template>         

</xsl:stylesheet>

应用于您的输入示例,这将返回:

结果

<html>
   <body>
      <table border="1">
         <tr>
            <th>Management Name</th>
            <th>Upravlinnya Name</th>
            <th>Viddil Name</th>
            <th>Name</th>
            <th>Surname</th>
            <th>Birth Year</th>
         </tr>
         <tr>
            <td rowspan="8">Management_1</td>
         </tr>
         <tr>
            <td rowspan="7">Upravlinnya_1</td>
         </tr>
         <tr>
            <td rowspan="4">Viddil_1</td>
         </tr>
         <tr>
            <td>Sviatoslav</td>
            <td>Kondera</td>
            <td>2002</td>
         </tr>
         <tr>
            <td>Orest</td>
            <td>Rodcevich</td>
            <td>1999</td>
         </tr>
         <tr>
            <td>Olena</td>
            <td>Zelenska</td>
            <td>1978</td>
         </tr>
         <tr>
            <td rowspan="2">Viddil_17</td>
         </tr>
         <tr>
            <td>SviatoslavNew</td>
            <td>KonderaNew</td>
            <td>2012</td>
         </tr>
         <tr>
            <td rowspan="5">Management_2</td>
         </tr>
         <tr>
            <td rowspan="4">Upravlinnya_2</td>
         </tr>
         <tr>
            <td rowspan="3">Viddil_2</td>
         </tr>
         <tr>
            <td>Nidia</td>
            <td>Dorofeeva</td>
            <td>2016</td>
         </tr>
         <tr>
            <td>Petro</td>
            <td>Poroshenko</td>
            <td>1976</td>
         </tr>
         <tr>
            <td rowspan="6">Management_333</td>
         </tr>
         <tr>
            <td rowspan="5">Upravlinnya_222</td>
         </tr>
         <tr>
            <td rowspan="2">Viddil_222</td>
         </tr>
         <tr>
            <td>Marsha</td>
            <td>May</td>
            <td>1995</td>
         </tr>
         <tr>
            <td rowspan="2">Viddil_212</td>
         </tr>
         <tr>
            <td>MarshaNew</td>
            <td>MayNew</td>
            <td>1905</td>
         </tr>
      </table>
   </body>
</html>

渲染

在此处输入图像描述


请注意,这不是一个严格正确的解决方案。理想情况下,每个部分的第一行应包含表中每一列的单元格,同样,每个子部分的第一行应包含该子部分列右侧剩余的每一列的单元格。

正因为如此,结果是非常轻微的倾斜:同一行中单元格的顶部边框没有完美对齐。但是,我相信为如此简单的代码付出的代价很小。


推荐阅读