匹配 XSL 中的子元素 [英] Matching child elements in XSL
问题描述
我以为我在 这个问题,并指出.有人告诉我我错了,我的回答后来被删除了.
I thought I saw a mistake in an answer to this question, and pointed it out. I was told I was incorrect, and my answer was later deleted.
我仍然不明白我错在哪里.因此,我在这里发帖,希望有人能解释我的误解.
I still don't see how I was wrong. Therefore, I am posting here and hoping someone can explain my misunderstanding to me.
我回复的答案解释了apply-templates的使用.它包含以下 XML 和 XSL,描述了模板的匹配方式:
The answer I responded to explained the use of apply-templates. It contained the following XML and XSL, describing how the templates would be matched:
<!-- sample XML snippet -->
<xml>
<foo /><bar /><baz />
</xml>
<!-- sample XSLT snippet -->
<xsl:template match="xml">
<xsl:apply-templates select="*" /> <!-- three nodes selected here -->
</xsl:template>
<xsl:template match="foo"> <!-- will be called once -->
<xsl:text>foo element encountered</xsl:text>
</xsl:template>
<xsl:template match="xml/*"> <!-- will be called twice -->
<xsl:text>other element countered</xsl:text>
</xsl:template>
我的评论是最后一个模板应该是:
My comment was that the last template in should be:
<xsl:template match="*"> <!-- will be called twice -->
<xsl:text>other element countered</xsl:text>
</xsl:template>
因为当前节点已经是
有人告诉我:
不,xml/* 是匹配元素的子元素的模式名称 xml.
No, xml/* is a pattern that matches child elements of an element with the name xml.
测试原始答案
但是,使用此 XML:
However, with this XML:
<xml>
<foo /><bar /><baz />
</xml>
还有这个 XSL 样式表(填写上面的片段):
And this XSL stylesheet (filling out the snippet above):
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="text"/>
<xsl:template match="xml">
<xsl:apply-templates select="*" /> <!-- three nodes selected here -->
</xsl:template>
<xsl:template match="foo"> <!-- will be called once -->
<xsl:text>foo element encountered.
</xsl:text>
</xsl:template>
<xsl:template match="xml/*"> <!-- will be called twice -->
<xsl:text>other element countered.
</xsl:text>
</xsl:template>
</xsl:stylesheet>
我明白了:
other element countered.
other element countered.
other element countered.
测试我的更正"版本
如果我将最后一个模板替换为:
If I replace the last template with:
<xsl:template match="*"> <!-- will be called twice -->
<xsl:text>other element countered.
</xsl:text>
</xsl:template>
根据我的回答,我得到:
as per my answer I get:
foo element encountered.
other element countered.
other element countered.
这似乎是正确的.
我希望我的问题没有违反任何准则,但我看不出我错了,希望有人能更全面地解释一下.
I hope my question doesn't break any guidelines, but I can't see that I'm wrong and am hoping someone can explain it more fully.
附注.恐怕我对另一个问题的原始回复是作为答案而不是评论发布的,因为我还没有足够的分数来发表评论.我不确定最好的做法是什么...
PS. I'm afraid my original response on the other question was posted as an answer, not a comment, as I don't have enough points to post comments yet. I wasn't sure what the best thing was to do...
推荐答案
这是正确的,根据 关于默认的规则模板的优先级.匹配 foo
的模板默认优先级为 0,匹配 *
的模板默认优先级为 -0.5,但匹配 xml/*
的模板默认优先级为 0.5.xml/*
模板被认为比 foo
模板更具体,因此当两者匹配时它就会获胜.
This is correct, according to the rules on the default priority of templates. A template matching foo
has default priority 0, one matching *
has default priority -0.5, but one matching xml/*
has default priority 0.5. The xml/*
template is considered more specific than the foo
one, so it wins when either could match.
所以你是对的,模板的匹配表达式需要是 *
而不是 xml/*
,但不是出于正确的原因 - xml/*
模板 can 匹配一个 apply-templates select="*"
当当前节点是 xml
时,它将应用于任何这些选定元素(因为它们都是 xml
的子元素),除非有另一个模板的显式 priority
大于 0.5 可以优先.
So you were right that the template's match expression needed to be *
rather than xml/*
, but not for the right reason - an xml/*
template can match for an apply-templates select="*"
when the current node is xml
, and it will apply to any of those selected elements (since they are all children of xml
) except where there is another template with an explicit priority
greater than 0.5 that can take precedence.
这篇关于匹配 XSL 中的子元素的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!