我正在尝试从for-each中访问变量。我今天做了很多阅读,试图弄清楚这一点,但没有什么比我的情况更合适。最终,我将有如下所示的多个系列,我将使用我正在拉出的变量并制作不同的条件。我在下面的for-each将从400条记录中恢复数据。对不起,我无法提供XML。我无法公开GUID等。
更新
var
p1 = Paranoiac.create({width: 55, height: 66}),
p2 = Paranoiac.create({width: 44, height: 77}),
p3 = Paranoiac.create({width: 33, height: 99})
;
console.log("Object.keys(p1) - ", Object.keys(p1));
console.log("Object.keys(p2) - ", Object.keys(p2));
console.log("Object.keys(p3) - ", Object.keys(p3));
console.log("p1.getWidth(), p1.getHeight() - ", [p1.getWidth(), p1.getHeight()]);
console.log("p2.getWidth(), p2.getHeight() - ", [p2.getWidth(), p2.getHeight()]);
console.log("p3.getWidth(), p3.getHeight() - ", [p3.getWidth(), p3.getHeight()]);
console.log('p1.setWidth("5"), p1.setHeight("6") - ', [p1.setWidth("5"), p1.setHeight("6")]);
console.log("p1.getWidth(), p1.getHeight() - ", [p1.getWidth(), p1.getHeight()]);
console.log("p2.getWidth(), p2.getHeight() - ", [p2.getWidth(), p2.getHeight()]);
console.log("p3.getWidth(), p3.getHeight() - ", [p3.getWidth(), p3.getHeight()]);
console.log('p2.setWidth("4"), p2.setHeight("7") - ', [p2.setWidth("4"), p2.setHeight("7")]);
console.log('p3.setWidth("3"), p3.setHeight("9") - ', [p3.setWidth("3"), p3.setHeight("9")]);
console.log("p1.getWidth(), p1.getHeight() - ", [p1.getWidth(), p1.getHeight()]);
console.log("p2.getWidth(), p2.getHeight() - ", [p2.getWidth(), p2.getHeight()]);
console.log("p3.getWidth(), p3.getHeight() - ", [p3.getWidth(), p3.getHeight()]);
console.log("Paranoiac.isParanoiac(p1) - ", Paranoiac.isParanoiac(p1));
console.log("Paranoiac.isParanoiac(p2) - ", Paranoiac.isParanoiac(p2));
console.log("Paranoiac.isParanoiac(p3) - ", Paranoiac.isParanoiac(p3));
console.log("Paranoiac.isParanoiac() - ", Paranoiac.isParanoiac());
console.log("Paranoiac.isParanoiac({}) - ", Paranoiac.isParanoiac({}));
所需的输出是任何具有$ findingName1等于$ rocName1的findsID。 GUID只出现一次,但每个级别都有数百条记录。
答案 0 :(得分:2)
我试图从for-each中访问变量。
变量$rocRecord
在for-each中的范围内。您可以简单地引用它并使用它。
但我认为你正在尝试做别的事情。即,为每个人定义一个变量 ,并希望在之外使用
。变量的范围包含其焦点设置包含块。所以简短的回答是:你不能这样做。但答案很长......
使用模板。做你似乎想要做的事情的唯一原因是需要访问其他地方的数据:
<xsl:template match="/">
<!-- in fact, you don't need for-each at all, but I leave it in for clarity -->
<xsl:for-each select="records/record">
<!--
apply-templates means: call the declared xsl:template that
matches this node, it is somewhat similar to a function call in other
languages, except that it works the other way around, the processor will
magically find the "function" (i.e., template) for you
-->
<xsl:apply-templates select="Field[@guid='123']" />
</xsl:for-each>
</xsl:template>
<xsl:template match="Field">
<!-- the focus here is what is the contents of your variable $rocName1 -->
<rocName>
<xsl:value-of select="substring=-before(., ' - ')" />
</rocName>
</xsl:template>
XSLT是一种声明性的,面向模板的函数式语言,与大多数其他语言相比,其概念非常独特。可能需要几个小时才能适应它。
你说你做过很多阅读,但也许是时候检查一下XSLT课程了吗?有一些在线,搜索&#34; XSLT基础课程&#34;。它会为你节省数小时/天的挫折感。
这是一个很好的,简短的阅读to catch up on variables in XSLT。
在第二次阅读时,我认为你看起来很麻烦,因为循环继续进行400项,而你只想输出$rocName1
的值。我在上面展示的示例确实如此,因为如果选择为空,则apply-templates不会执行任何操作,如果找不到guid会发生这种情况。
如果guid出现一次,上面的代码将输出一次。如果它出现多次并且您只想要第一个,请将[1]
附加到select语句。
你有两个循环:
<xsl:for-each select="Records/Record/Record[@levelGuid = 'level1']">
和
<xsl:for-each select="Records/Record/Record[@levelGuid = 'levelA']">
当第一个循环中的记录与第二个循环中的记录匹配时,您想要做某事(创建findingId
)。
虽然你可以使用(嵌套)循环来解决这个问题,但是没有必要这样做,事实上,不鼓励它,因为它会使你的代码难以阅读。正如我在原始答案中所解释的那样,apply-templates通常是更简单的方法来实现这一点。
由于Record
元素是彼此的兄弟姐妹,我将按如下方式处理:
<xsl:template match="/">
<Records>
<xsl:apply-templates select="Records/Records/Record[@levelGuid = 'level1']" />
</Records>
</xsl:template>
<xsl:template match="Record">
<xsl:variable name="rocName1" select="Field[@guid = '123']"/>
<xsl:variable name ="rocName2" select="substring-before($rocName1, ' - ')"/>
<xsl:variable name="findingNameBase" select="../Record[@levelGuid = 'levelA']" />
<xsl:variable name ="findingName" select="$findingNameBase/Field[@guid = '123']"/>
<xsl:variable name="findingName1" select="substring-after($findingName, ': ')"/>
<xsl:variable name="findingName2" select="substring-after($findingName1, 'PCIDSSv3.1:')"/>
<findingId rocName="{$rocName1}">
<xsl:value-of select="$findingName" />
</findingId>
</xsl:template>
虽然这可以进一步简化,但是学习应用模板是一个很好的开始,这是你使用XSLT做的任何事情的核心。 Learn about applying templates,因为没有它,XSLT将很难理解。