2012-05-03 26 views
13

我正在尝试编写一个XSL,它将从源XML中输出特定的子字段。通过使用包含字段名称的外部XML配置文档以及其他特定信息(例如填充长度),可以在转换时间确定该子集。为每个循环嵌套,从内部循环访问具有变量的外部元素

所以,这是二for-each循环:

  • 在记录外一个迭代通过记录来访问他们的场纪录。
  • 内层迭代配置XML文档以从当前记录中获取已配置的字段。

我在In XSLT how do I access elements from the outer loop from within nested loops?中看到,外部循环中的当前元素可以存储在xsl:variable中。但是,我必须在内部循环中定义一个新变量来获取字段名称。这就产生了这样的问题:是否有可能访问一个有两个变量的路径?

例如,源XML文档的样子:

<data> 
    <dataset> 
     <record> 
      <field1>value1</field1> 
      ... 
      <fieldN>valueN</fieldN> 
     </record> 
    </dataset> 
    <dataset> 
     <record> 
      <field1>value1</field1> 
      ... 
      <fieldN>valueN</fieldN> 
     </record> 
    </dataset> 
</data> 

我想有一个外部XML文件看起来像:

<configuration> 
    <outputField order="1"> 
     <fieldName>field1</fieldName> 
     <fieldPadding>25</fieldPadding> 
    </outputField> 
    ... 
    <outputField order="N"> 
     <fieldName>fieldN</fieldName> 
     <fieldPadding>10</fieldPadding> 
    </outputField> 
</configuration> 

的XSL到目前为止我有:

<xsl:variable name="config" select="document('./configuration.xml')"/> 
<xsl:for-each select="data/dataset/record"> 
    <!-- Store the current record in a variable --> 
    <xsl:variable name="rec" select="."/> 
    <xsl:for-each select="$config/configuration/outputField"> 
     <xsl:variable name="field" select="fieldName"/> 
     <xsl:variable name="padding" select="fieldPadding"/> 

     <!-- Here's trouble --> 
     <xsl:variable name="value" select="$rec/$field"/> 

     <xsl:call-template name="append-pad"> 
      <xsl:with-param name="padChar" select="$padChar"/> 
      <xsl:with-param name="padVar" select="$value"/> 
      <xsl:with-param name="length" select="$padding"/> 
     </xsl:call-template> 

    </xsl:for-each> 
    <xsl:value-of select="$newline"/> 
</xsl:for-each> 

我对XSL相当陌生,所以这可能是一个荒谬的问题,而且这种方法也可以是普通的ng(即重新开始内部循环,以便在开始时可以完成一次任务)。我会很感激有关如何从外部循环元素中选择字段值的任何提示,当然,也可以采用更好的方法来处理此任务。

回答

13

你的样式表看起来很好。只是表达式$rec/$field没有意义,因为您无法以这种方式组合两个节点集/序列。相反,您应该使用name()函数比较元素的名称。如果我理解正确的话您的问题,这样的事情应该工作:在这个例子中,不需要

<xsl:variable name="config" select="document('./configuration.xml')"/> 
<xsl:for-each select="data/dataset/record"> 
    <xsl:variable name="rec" select="."/> 
    <xsl:for-each select="$config/configuration/outputField"> 
     <xsl:variable name="field" select="fieldName"/> 
     ... 
     <xsl:variable name="value" select="$rec/*[name(.)=$field]"/> 
     ...  
    </xsl:for-each> 
    <xsl:value-of select="$newline"/> 
</xsl:for-each> 

可变。您还可以使用功能current()访问内部循环的当前上下文节点:

<xsl:variable name="value" select="$rec/*[name(.)=current()/fieldName]"/>