使用相似参数调用模板两次
call template twice with similar parameters
现在我有一个这样的 xml 文件:
基本上所有的标签都会出现两次,但是前缀是 sideA
或 sideB
<root>
<sideA_foo>abc</sideA_foo>
<sideA_bar>123</sideA_bar>
<sideA_foobar>xyz</sideA_foobar>
<!--many more sideA... tags -->
<sideB_foo>def</sideB_foo>
<sideB_bar>456</sideB_bar>
<sideB_foobar>uvw</sideB_foobar>
<!--many more sideB... tags -->
</root>
那我就有了这样的模板
<xsl:template name="template1">
<xsl:param name = "foo"/>
<xsl:param name = "bar"/>
<xsl:param name = "foobar"/>
<!-- many more params -->
<!-- do anything here -->
</xsl:template>
有没有一种优雅的方法可以用它的所有参数调用这个模板两次,
<xsl:with-param name = "foo" select = "sideA_foo"/>
等
<xsl:with-param name = "foo" select = "sideB_foo"/>
等
没有把所有这些都写得非常冗长,我讨厌这样?
这是您可以考虑的一种方法:
给定一个示例输入:
<root>
<sideA_width>5</sideA_width>
<sideA_length>7</sideA_length>
<sideB_width>6</sideB_width>
<sideB_length>3</sideB_length>
</root>
以下样式表:
<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="/root">
<output>
<xsl:call-template name="side-area">
<xsl:with-param name="side" select="'sideA'"/>
</xsl:call-template>
<xsl:call-template name="side-area">
<xsl:with-param name="side" select="'sideB'"/>
</xsl:call-template>
</output>
</xsl:template>
<xsl:template name="side-area">
<xsl:param name="side"/>
<xsl:param name="width" select="*[name()=concat($side, '_width')]"/>
<xsl:param name="length" select="*[name()=concat($side, '_length')]"/>
<xsl:element name="{$side}_area">
<xsl:value-of select="$width * $length"/>
</xsl:element>
</xsl:template>
</xsl:stylesheet>
将return:
<?xml version="1.0" encoding="UTF-8"?>
<output>
<sideA_area>35</sideA_area>
<sideB_area>18</sideB_area>
</output>
但是请注意,元素的显式命名更有效 - 有时 很多 更有效。 真正 优雅的解决方案是在输入到达您之前对其进行规范化,这样它看起来更像(例如):
<root>
<rect id="X">
<width>5</width>
<length>7</length>
</rect>
<rect id="Y">
<width>6</width>
<length>3</length>
</rect>
</root>
现在我有一个这样的 xml 文件:
基本上所有的标签都会出现两次,但是前缀是 sideA
或 sideB
<root>
<sideA_foo>abc</sideA_foo>
<sideA_bar>123</sideA_bar>
<sideA_foobar>xyz</sideA_foobar>
<!--many more sideA... tags -->
<sideB_foo>def</sideB_foo>
<sideB_bar>456</sideB_bar>
<sideB_foobar>uvw</sideB_foobar>
<!--many more sideB... tags -->
</root>
那我就有了这样的模板
<xsl:template name="template1">
<xsl:param name = "foo"/>
<xsl:param name = "bar"/>
<xsl:param name = "foobar"/>
<!-- many more params -->
<!-- do anything here -->
</xsl:template>
有没有一种优雅的方法可以用它的所有参数调用这个模板两次,
<xsl:with-param name = "foo" select = "sideA_foo"/>
等<xsl:with-param name = "foo" select = "sideB_foo"/>
等
没有把所有这些都写得非常冗长,我讨厌这样?
这是您可以考虑的一种方法:
给定一个示例输入:
<root>
<sideA_width>5</sideA_width>
<sideA_length>7</sideA_length>
<sideB_width>6</sideB_width>
<sideB_length>3</sideB_length>
</root>
以下样式表:
<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="/root">
<output>
<xsl:call-template name="side-area">
<xsl:with-param name="side" select="'sideA'"/>
</xsl:call-template>
<xsl:call-template name="side-area">
<xsl:with-param name="side" select="'sideB'"/>
</xsl:call-template>
</output>
</xsl:template>
<xsl:template name="side-area">
<xsl:param name="side"/>
<xsl:param name="width" select="*[name()=concat($side, '_width')]"/>
<xsl:param name="length" select="*[name()=concat($side, '_length')]"/>
<xsl:element name="{$side}_area">
<xsl:value-of select="$width * $length"/>
</xsl:element>
</xsl:template>
</xsl:stylesheet>
将return:
<?xml version="1.0" encoding="UTF-8"?>
<output>
<sideA_area>35</sideA_area>
<sideB_area>18</sideB_area>
</output>
但是请注意,元素的显式命名更有效 - 有时 很多 更有效。 真正 优雅的解决方案是在输入到达您之前对其进行规范化,这样它看起来更像(例如):
<root>
<rect id="X">
<width>5</width>
<length>7</length>
</rect>
<rect id="Y">
<width>6</width>
<length>3</length>
</rect>
</root>