You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在xsl:if中实现类似SQL IN的多值条件匹配功能?

XSLT 1.0实现类似SQL IN多值判断的方法

你不需要写一堆重复的<xsl:if>,以下三种方案都可以实现多值列表匹配,按推荐优先级排序:


方案1:XPath原生节点集匹配(推荐,易维护)

XPath本身就支持单值和节点集的比较规则:当等号左边是单个值,右边是节点集合时,只要集合里任意一个节点的值和左边相等,整个判断就返回true,这个逻辑和SQL的IN完全一致。
针对你20个值映射到3个目标字段的场景,这个方案维护成本最低:

  1. 首先在样式表根节点加EXSLT通用命名空间声明(绝大多数XSLT 1.0引擎比如libxslt、Xalan、Saxon 6都原生支持这个扩展,无兼容问题):
    <xsl:stylesheet 
      xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
      xmlns:exslt="http://exslt.org/common"
      version="1.0">
    
  2. 把三个分组的匹配值集中定义为变量,后续改映射规则只需要调整变量内容:
    <!-- 映射到crs_udf5.crs.srs的取值列表 -->
    <xsl:variable name="mapUdf5">
      <v>01</v><v>02</v><v>43</v>
      <!-- 补充所有归到该分组的取值 -->
    </xsl:variable>
    <!-- 映射到crs_udf6.crs.srs的取值列表 -->
    <xsl:variable name="mapUdf6">
      <v>03</v><v>07</v><v>22</v>
      <!-- 补充所有归到该分组的取值 -->
    </xsl:variable>
    <!-- 映射到crs_udf7.crs.srs的取值列表 -->
    <xsl:variable name="mapUdf7">
      <v>04</v><v>09</v><v>35</v>
      <!-- 补充所有归到该分组的取值 -->
    </xsl:variable>
    
  3. 判断时直接用节点集比较逻辑,替换原来的单值if判断即可:
    <xsl:variable name="currSrs" select="..//sce_moac.sce.srs"/>
    <xsl:choose>
      <xsl:when test="$currSrs = exslt:node-set($mapUdf5)/v">
        <xsl:value-of select="../../..//crs_udf5.crs.srs"/>
      </xsl:when>
      <xsl:when test="$currSrs = exslt:node-set($mapUdf6)/v">
        <xsl:value-of select="../../..//crs_udf6.crs.srs"/>
      </xsl:when>
      <xsl:when test="$currSrs = exslt:node-set($mapUdf7)/v">
        <xsl:value-of select="../../..//crs_udf7.crs.srs"/>
      </xsl:when>
    </xsl:choose>
    

方案2:or逻辑直接拼接(兼容性最高)

如果你的运行环境不支持任何扩展函数,直接把多个判断条件用or拼接即可,不需要额外依赖:

<xsl:if test="..//sce_moac.sce.srs='01' 
  or ..//sce_moac.sce.srs='02' 
  or ..//sce_moac.sce.srs='43'">
  <xsl:value-of select="../../..//crs_udf5.crs.srs"/>
</xsl:if>

这个写法的缺点是值多了代码冗余度高,后续调整值需要改判断逻辑,适合值数量少的场景。


方案3:contains字符串匹配(无扩展兼容方案)

如果不能用EXSLT的node-set函数,也可以用字符串包含判断实现,必须加分隔符避免子串误匹配:

<!-- 所有值前后都加|分隔,避免短值误匹配长值的子串 -->
<xsl:variable name="udf5List" select="'|01|02|43|'"/>
<xsl:if test="contains($udf5List, concat('|', ..//sce_moac.sce.srs, '|'))">
  <xsl:value-of select="../../..//crs_udf5.crs.srs"/>
</xsl:if>

注意:不要省略前后的分隔符,否则会出现比如判断值为1时,误匹配到列表里11这类值的问题。


额外提醒

你提供的示例XSL里写了两个匹配根节点/的模板,XSLT会用后定义的模板覆盖前面的,前面那个只写了<xsl:apply-templates />的根模板完全无效,可以直接删掉避免冲突。

内容的提问来源于stack exchange,提问作者jonah

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.31 00:03:19