2011-09-05 55 views
7

問題是使用XSL合併和排序多個XML文件並輸出有效的HTML,可用Firefox> = 3.5查看,如果可能的話IE> = 7。答案應該儘可能簡單(性能不重要)。使用XSL合併和排序多個XML文件

文件A.XML

<?xml version="1.0"?> 
<root> 
    <tag>cc</tag> 
    <tag>aa</tag> 
</root> 

文件B.XML

<?xml version="1.0"?> 
<root> 
    <tag>xx</tag> 
    <tag>bb</tag> 
</root> 

文件INDEX.XML

<?xml version="1.0"?> 
<?xml-stylesheet type="text/xsl" href="merge.xslt"?> 
<list> 
    <entry>a.xml</entry> 
    <entry>b.xml</entry> 
</list> 

文件merge.xslt

<?xml version="1.0"?> 
<xsl:stylesheet version="1.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:ph="http://ananas.org/2003/tips/photo"> 

    <xsl:output method="html"/> 

    <xsl:template match="list"> 
     <html> 
      <body> 
       <xsl:apply-templates/> 
      </body> 
     </html> 
    </xsl:template> 

    <xsl:template match="entry"> 
     <xsl:for-each select="document(.)/root/tag"> 
      <!-- This will only sort the values of a single file --> 
      <xsl:sort select="." data-type="text" order="ascending" /> 
      - <xsl:value-of select="."/> <br/> 
     </xsl:for-each> 
    </xsl:template> 
</xsl:stylesheet> 

電流輸出:

  • AA

  • 立方厘米

  • BB

  • XX

預期輸出:

  • AA

  • BB

  • 立方厘米

  • XX

+1

好問題,+1。看到我的答案是一個完整的,非常簡短的解決方案,沒有任何其他答案的複雜性:沒有擴展功能,沒有變量,沒有'xsl:for-each' ...... –

+0

還添加了大量的解釋。 –

回答

8

對此的解決方案是非常短的並且容易變換(絕對沒有擴展功能a再需要):

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

<xsl:template match="/*"> 
    <html> 
    <ul> 
    <xsl:apply-templates 
     select="document(entry)/*/tag"> 
     <xsl:sort/> 
    </xsl:apply-templates> 
    </ul> 
    </html> 
</xsl:template> 

<xsl:template match="tag"> 
    <li><xsl:value-of select="."/></li> 
</xsl:template> 
</xsl:stylesheet> 

當這種轉化應用所提供的指數。XML文件

<list> 
    <entry>a.xml</entry> 
    <entry>b.xml</entry> 
</list> 

想要的,正確的結果產生

<html> 
    <ul> 
     <li>aa</li> 
     <li>bb</li> 
     <li>cc</li> 
     <li>xx</li> 
    </ul> 
</html> 

,它顯示在任何瀏覽器

  • AA
  • BB
  • 立方厘米
  • XX

說明該解決方案使用標準的XSLT功能document()的功率。如W3C XSLT 1.0建議書所定義:

當文檔函數有且只有一個參數和參數 是一個節點集合,那麼結果是工會,在 參數的每個節點節點 - 設置調用文件的功能與 的第一個參數是一個節點的字串值的結果,

這說明我們的代碼這個片段的效果:

<xsl:apply-templates 
    select="document(entry)/*/tag"> 
    <xsl:sort/> 
</xsl:apply-templates> 

這裏發生的是document()函數的參數是index.xml頂部元素的所有entry子元素的節點集。結果是所有文檔節點的聯合。

因此

select="document(entry)/*/tag" 

選擇在index.xml參考的所有文件都tag元素。然後對它們進行排序(按xsl:sort),並且已排序的節點列表中的每個元素都由匹配tag的模板處理。

+0

已接受,因爲答案有效且易於理解。非常好的解釋! – gaddomn

+1

我不知道爲什麼我這麼複雜。我需要休息一會兒。最佳和簡單的方法+1。 –

+0

@gaddomn:不客氣。 @_empo:你也是。 –