2014-11-02 180 views
0

我的XML是:XSL分組標記爲母公司

<Row> 
     <one>1</one> 
     <two>2</two> 
     <three>3</tree> 
     <four>4</four> 
     <... 
     <... 
     <... 
    </Row> 

和我預期的結果是:

<Row> 
    <main> 
      <value type="one_type"> 
       <stringValue>1</stringValue> 
      </value> 
      <value type="two_type"> 
       <stringValue>2</stringValue> 
      </value> 
     </main> 

<others> 
     <three>3</tree> 
     <four>4</four> 
     <... 
     <... 
     <... 
<others> 

</Row> 

和我的XSL是:

<xsl:template match="node()|@*"> 
     <xsl:copy> 
      <xsl:apply-templates select="node()|@*"/> 
     </xsl:copy> 
    </xsl:template> 


    <xsl:template match="one|two"> 
    <main> 
     <xsl:choose> 
      <xsl:when test="one"> 
       <value type="one_type"> 
        <stringValue> 
         <xsl:apply-templates select="@*|node()"/> 
        </stringValue> 
       </value> 
      </xsl:when> 
      <xsl:otherwise> 
       <value type="two_type"> 
        <stringValue> 
         <xsl:apply-templates select="@*|node()"/> 
        </stringValue> 
       </value> 
      </xsl:otherwise> 
     </xsl:choose> 
    </main> 

    </xsl:template> 

但這返回兩個不同的主標籤,我希望所有標籤都在主標籤下。 任何想法如何做到這一點?我想如果別人會給我想要的結果,但它不會。

回答

0

你可以得到所需的輸出與以下調整

<?xml version="1.0" encoding="utf-8"?> 
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" > 
<xsl:output method="xml" omit-xml-declaration="yes" encoding="UTF-8" indent="yes"/> 
<xsl:template match="node()|@*"> 
    <xsl:copy> 
     <xsl:apply-templates select="node()|@*"/> 
    </xsl:copy> 
</xsl:template> 
<xsl:template match="Row"> 
    <main> 
     <xsl:apply-templates select="node()|@*"/> 
    </main> 
</xsl:template> 
<xsl:template match="one|two"> 
    <xsl:choose> 
     <xsl:when test="local-name() = 'one'"> 
      <value type="one_type"> 
       <stringValue> 
        <xsl:apply-templates select="@*|node()"/> 
       </stringValue> 
      </value> 
     </xsl:when> 
     <xsl:otherwise> 
      <value type="two_type"> 
       <stringValue> 
        <xsl:apply-templates select="@*|node()"/> 
       </stringValue> 
      </value> 
     </xsl:otherwise> 
    </xsl:choose> 
</xsl:template> 
</xsl:stylesheet> 

輸入:

<Row> 
    <one>1</one> 
    <two>2</two> 
</Row> 

輸出繼電器:

<main> 
<value type="one_type"> 
    <stringValue>1</stringValue> 
</value> 
<value type="two_type"> 
    <stringValue>2</stringValue> 
</value> 
</main> 

所以元素main只能寫一次 - 在附加模板匹配 - 作爲其他ele的包裝由當前模板匹配onetwo寫入。

更新爲所編輯的問題:

XSLT:

<?xml version="1.0" encoding="utf-8"?> 
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" > 
<xsl:output method="xml" omit-xml-declaration="yes" encoding="UTF-8" indent="yes"/> 
<xsl:template match="node()|@*"> 
    <xsl:copy> 
     <xsl:apply-templates select="node()|@*"/> 
    </xsl:copy> 
</xsl:template> 
<xsl:template match="Row"> 
<Row> 
    <main> 
     <xsl:apply-templates select="one | two "/> 
    </main> 
    <xsl:apply-templates select="three| four"/> 
</Row> 
</xsl:template> 
<xsl:template match="one|two"> 
    <xsl:choose> 
     <xsl:when test="local-name() = 'one'"> 
      <value type="one_type"> 
       <stringValue> 
        <xsl:apply-templates select="@*|node()"/> 
       </stringValue> 
      </value> 
     </xsl:when> 
     <xsl:otherwise> 
      <value type="two_type"> 
       <stringValue> 
        <xsl:apply-templates select="@*|node()"/> 
       </stringValue> 
      </value> 
     </xsl:otherwise> 
    </xsl:choose> 
</xsl:template> 
<xsl:template match="three|four"> 
    <xsl:copy-of select="."/> 
</xsl:template> 
</xsl:stylesheet> 

輸入:

<Row> 
    <one>1</one> 
    <two>2</two> 
    <three>1</three> 
    <four>2</four> 
</Row> 

輸出:

<Row> 
<main> 
    <value type="one_type"> 
    <stringValue>1</stringValue> 
    </value> 
    <value type="two_type"> 
    <stringValue>2</stringValue> 
    </value> 
</main> 
<three>1</three> 
<four>2</four> 
</Row> 

更新爲OP的第二調整:

作爲示例輸入XML爲6個條目:

輸入:

<Row> 
    <one>1</one> 
    <two>2</two> 
    <three>3</three> 
    <four>4</four> 
    <five>5</five> 
    <six>6</six> 
</Row> 

XSLT:

<?xml version="1.0" encoding="utf-8"?> 
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" > 
<xsl:output method="xml" omit-xml-declaration="yes" encoding="UTF-8" indent="yes"/> 
<xsl:template match="node()|@*"> 
    <xsl:copy> 
     <xsl:apply-templates select="node()|@*"/> 
    </xsl:copy> 
</xsl:template> 
<xsl:template match="Row"> 
<Row> 
    <main> 
     <xsl:apply-templates select="one | two "/> 
    </main> 
    <xsl:apply-templates select="node()[not(self::one | self::two)]"/> 
</Row> 
</xsl:template> 
<xsl:template match="one|two"> 
    <xsl:choose> 
     <xsl:when test="local-name() = 'one'"> 
      <value type="one_type"> 
       <stringValue> 
        <xsl:apply-templates select="@*|node()"/> 
       </stringValue> 
      </value> 
     </xsl:when> 
     <xsl:otherwise> 
      <value type="two_type"> 
       <stringValue> 
        <xsl:apply-templates select="@*|node()"/> 
       </stringValue> 
      </value> 
     </xsl:otherwise> 
    </xsl:choose> 
</xsl:template> 
<xsl:template match="node()"> 
    <xsl:copy-of select="."/> 
</xsl:template> 
</xsl:stylesheet> 

輸出:

<Row> 
<main> 
    <value type="one_type"> 
    <stringValue>1</stringValue> 
    </value> 
    <value type="two_type"> 
    <stringValue>2</stringValue> 
    </value> 
</main> 
<three>3</three> 
<four>4</four> 
<five>5</five> 
<six>6</six> 
</Row> 

調整是在使用<xsl:apply-templates select="node()[not(self::one | self::two)]"/>和更改模板,只是複製main標籤下方的節點,以匹配所有節點匹配row,除了命名爲onetwo元素的所有節點模板應用模板 - <xsl:template match="node()">

+0

這裏的結果是兩次 「two_type」,「one_type 「已經不存在了...... – lshaked 2014-11-02 12:58:56

+0

如果你真的想在模板裏做一個測試,那麼你測試=」self :: one「'。但通常寫一個匹配模式就足夠了。 – 2014-11-02 13:11:37

+0

@ user3379892感謝您的輸入,只是更新了我的答案。 – 2014-11-02 13:11:57

0

我不在該樣本中看不到任何分組,您似乎想要變換至mainonevalue type="one_type"twovalue type="two_type"

因此,與

<xsl:template match="node()|@*"> 
     <xsl:copy> 
      <xsl:apply-templates select="node()|@*"/> 
     </xsl:copy> 
    </xsl:template> 

你的開始是好的,再加入

<xsl:template match="Row"> 
    <main> 
    <xsl:apply-templates select="@* | node()"/> 
    </main> 
</xsl:template> 

然後

<xsl:template match="one | two"> 
    <value type="{local-name()}_type"> 
    <stringValue> 
     <xsl:apply-templates/> 
    </stringValue> 
    </value> 
</xsl:template> 
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:strip-space elements="*"/> 

<!-- identity transform --> 
<xsl:template match="@*|node()"> 
    <xsl:copy> 
     <xsl:apply-templates select="@*|node()"/> 
    </xsl:copy> 
</xsl:template> 

<xsl:template match="/Row"> 
    <xsl:copy> 
     <main> 
      <xsl:apply-templates select="one|two"/> 
     </main> 
     <xsl:apply-templates select="three|four"/> 
    </xsl:copy> 
</xsl:template> 

<xsl:template match="one|two"> 
    <value type="{local-name()}_type"> 
     <stringValue> 
      <xsl:value-of select="."/> 
     </stringValue> 
    </value> 
</xsl:template> 

</xsl:stylesheet> 

如果您不能確定哪個比其他元素<one><two>可以出現,改變這一行:

<xsl:apply-templates select="three|four"/> 

到:

<xsl:apply-templates select="*[not(self::one or self::two)]"/> 
+0

太棒了!這是有幫助的 – lshaked 2014-11-02 14:27:53

+0

@ user3379892 http://stackoverflow.com/help/someone-answers – 2014-11-02 14:31:55