xslt 获取紧随其后的同级
xslt get the immediate following sibling
我有以下内容:
<root>
<html>
<table
<tr>
<td width="1%" height="20"></td>
<td width="18%">Book Location </td>
<td width="81%">Technology (Applied sciences) Circulation</td>
</tr>
我正在尝试在 xslt 下获取直接节点内容,其中 td 的节点内容是 "Book Location ":
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0"
xmlns:marc="http://www.loc.gov/MARC21/slim"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="text" indent="yes" />
<xsl:template match="root">
<xsl:for-each select="html">
<xsl:text>START HERE</xsl:text>
<xsl:text> </xsl:text>
<xsl:text>=LDR 00000nam 2200000Ia 4500</xsl:text>
<xsl:text> </xsl:text>
<xsl:if test="//*[text()='Book Location ']">
<xsl:text>=952 \$cLocation: </xsl:text>
<xsl:value-of select="following-sibling" />
</xsl:if>
</xsl:for-each>
</xsl:template>
</xsl:stylesheet>
我不确定在这部分放什么:
或者是否有更好的方法来做到这一点?
提前致谢,祝您有愉快的一天!
你可以使用这个:
<xsl:value-of select="//*[text()='Book Location ']/following-sibling::*[1]" />
而不是
<xsl:value-of select="following-sibling" />
您的模板表明您正在像过程语言程序员一样思考。 XSLT 或多或少可以写成那种习语,但它不是 XSLT 的 natural 习语。以这种方式编写的代码往往比更自然的代码更长、更混乱。特别是,虽然它们有很好的用途,但 for-each
元素通常带有一点代码味道。
这对我来说似乎更自然,而且似乎有效(但我必须测试您输入的修改版本,因为您提供的内容无效 XML):
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="text" indent="yes" />
<xsl:template match="/root/html">
<xsl:text>START HERE</xsl:text>
<xsl:text> </xsl:text>
<xsl:text>=LDR 00000nam 2200000Ia 4500</xsl:text>
<xsl:text> </xsl:text>
<xsl:apply-templates select="descendant::td[text() = 'Book Location ']" />
</xsl:template>
<xsl:template match="td">
<xsl:text>=952 \$cLocation: </xsl:text>
<xsl:value-of select="following-sibling::*[1]" />
</xsl:template>
</xsl:stylesheet>
注:
- 一个更具体的匹配表达式消除了对
for-each
在你的原始 中的需要
- 与其尝试将整个转换放入一个模板,不如使用单独的模板来转换单独的元素。这不仅更清晰,而且有助于简化表达式,因为每个模板都与其自己的上下文相关联,相对于表达式进行评估
- 要使用 "following-sibling" 作为轴名称,而不是元素名称,您必须附加一个双冒号和至少某种节点测试
- "following-sibling" 轴可以包含多个节点,因此如果您只想要紧随其后的节点,则需要指定(如上所述)
- 我可能选择直接转换包含位置的
td
,而不是通过其标签 td
的模板间接转换。这对我来说似乎更干净,但我没有这样做,因为它的语义略有不同。
我有以下内容:
<root>
<html>
<table
<tr>
<td width="1%" height="20"></td>
<td width="18%">Book Location </td>
<td width="81%">Technology (Applied sciences) Circulation</td>
</tr>
我正在尝试在 xslt 下获取直接节点内容,其中 td 的节点内容是 "Book Location ":
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0"
xmlns:marc="http://www.loc.gov/MARC21/slim"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="text" indent="yes" />
<xsl:template match="root">
<xsl:for-each select="html">
<xsl:text>START HERE</xsl:text>
<xsl:text> </xsl:text>
<xsl:text>=LDR 00000nam 2200000Ia 4500</xsl:text>
<xsl:text> </xsl:text>
<xsl:if test="//*[text()='Book Location ']">
<xsl:text>=952 \$cLocation: </xsl:text>
<xsl:value-of select="following-sibling" />
</xsl:if>
</xsl:for-each>
</xsl:template>
</xsl:stylesheet>
我不确定在这部分放什么: 或者是否有更好的方法来做到这一点? 提前致谢,祝您有愉快的一天!
你可以使用这个:
<xsl:value-of select="//*[text()='Book Location ']/following-sibling::*[1]" />
而不是
<xsl:value-of select="following-sibling" />
您的模板表明您正在像过程语言程序员一样思考。 XSLT 或多或少可以写成那种习语,但它不是 XSLT 的 natural 习语。以这种方式编写的代码往往比更自然的代码更长、更混乱。特别是,虽然它们有很好的用途,但 for-each
元素通常带有一点代码味道。
这对我来说似乎更自然,而且似乎有效(但我必须测试您输入的修改版本,因为您提供的内容无效 XML):
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="text" indent="yes" />
<xsl:template match="/root/html">
<xsl:text>START HERE</xsl:text>
<xsl:text> </xsl:text>
<xsl:text>=LDR 00000nam 2200000Ia 4500</xsl:text>
<xsl:text> </xsl:text>
<xsl:apply-templates select="descendant::td[text() = 'Book Location ']" />
</xsl:template>
<xsl:template match="td">
<xsl:text>=952 \$cLocation: </xsl:text>
<xsl:value-of select="following-sibling::*[1]" />
</xsl:template>
</xsl:stylesheet>
注:
- 一个更具体的匹配表达式消除了对
for-each
在你的原始 中的需要
- 与其尝试将整个转换放入一个模板,不如使用单独的模板来转换单独的元素。这不仅更清晰,而且有助于简化表达式,因为每个模板都与其自己的上下文相关联,相对于表达式进行评估
- 要使用 "following-sibling" 作为轴名称,而不是元素名称,您必须附加一个双冒号和至少某种节点测试
- "following-sibling" 轴可以包含多个节点,因此如果您只想要紧随其后的节点,则需要指定(如上所述)
- 我可能选择直接转换包含位置的
td
,而不是通过其标签td
的模板间接转换。这对我来说似乎更干净,但我没有这样做,因为它的语义略有不同。