传送字符串数组,作为一个查询条件(即:mybatis中in用法)

采坑记录:

项目中需要需要用到传送一个List<String>,作为条件到mybatis中去查询数据,但是查出来一直是0条数据,此处我用的是StringJoiner来拼接的字符串,代码如下:

StringJoiner supperNoList = new StringJoiner(",");
    for (ExportScheduleAllModelsT jin : jinList) {
    String supperNo = jin.getSupperNo();
    strList.add(supperNo);
    supperNoList.add(supperNo);
    }

列印出来的结果是:supperNoList:E110952, E110978

然后使用toString()方法传送给XML
XML中是这样写的:

<select id="selectAllInfoContainsBySupperNo" resultType="com.davi.provider.entity.ExportScheduleT">
    select EXPORT_DATE, SUPPER_NO, DESCRIPTION, sum(QUANTITY) QUANTITY
     from B_EXPORT_SCHEDULE_T
     where EXPORT_DATE = #{exportDate,jdbcType=VARCHAR} and SUPPER_NO like 'E%' and SUPPER_NO in #{supperNo,jdbcType=VARCHAR}
       and (DESCRIPTION like '%HDH-S%' or DESCRIPTION like '%HAD-S%' or DESCRIPTION like '%HAT-S%' or DESCRIPTION like '%HEG-S%'
       or DESCRIPTION like '%HAC-R-AL3PA%' or DESCRIPTION like '%HAC-A-CDH%' or DESCRIPTION like '%HEG-A-CDH%')
     group by EXPORT_DATE, SUPPER_NO, DESCRIPTION
</select>

以上的参数传送方式,不能识别多个参数的情况,固不能使用这种方法。

正确方式:

将获取的值放在List里,如下:

List<String> strList = new ArrayList<>();
    for (ExportScheduleAllModelsT jin : jinList) {
          String supperNo = jin.getSupperNo();
          strList.add(supperNo);
         }
System.out.println("已經導入的strList:"+ strList);

列印处的结果为:已經導入的strList:[E110952, E110978]
XML中的写法:

<select id="selectAllInfoContainsBySupperNo" resultType="com.davi.provider.entity.ExportScheduleT">
    select EXPORT_DATE, SUPPER_NO, DESCRIPTION, sum(QUANTITY) QUANTITY
    from B_EXPORT_SCHEDULE_T
    where EXPORT_DATE = #{exportDate,jdbcType=VARCHAR} and SUPPER_NO like 'E%' and SUPPER_NO in
              <foreach item="supperNo" index="index" collection="strList"
                       open="(" separator="," close=")">
                #{supperNo,jdbcType=VARCHAR}
              </foreach>
      and (DESCRIPTION like '%HDH-S%' or DESCRIPTION like '%HAD-S%' or DESCRIPTION like '%HAT-S%' or DESCRIPTION like '%HEG-S%'
      or DESCRIPTION like '%HAC-R-AL3PA%' or DESCRIPTION like '%HAC-A-CDH%' or DESCRIPTION like '%HEG-A-CDH%')
    group by EXPORT_DATE, SUPPER_NO, DESCRIPTION
</select>

多种情况得总结:

在SQL开发过程中,动态构建In集合条件查询是比较常见的用法,在Mybatis中提供了foreach功能,该功能比较强大,它允许你指定一个集合,声明集合项和索引变量,它们可以用在元素体内。

它也允许你指定开放和关闭的字符串,在迭代之间放置分隔符。

关于Mybatis中in的写法,结合网上搜索到的和我遇到的,详细总结了一下

<foreach item="xxx" index="index"  collection="***" open="(" separator="," close=")">

 #{xxx}                

</foreach>

1.传递参数为单一list的写法,collection属性要必须指定为 list,如:

<foreach item="supperNo" index="index" collection="list"
                       open="(" separator="," close=")">
                #{supperNo,jdbcType=VARCHAR}
              </foreach>

2.传递参数为单一数组的写法,collection属性要必须指定为 array,如:

<foreach item="supperNo" index="index" collection="strList"
                       open="(" separator="," close=")">
                #{supperNo,jdbcType=VARCHAR}
              </foreach>

需要特别说明的是mapper层是这样的:

List<ExportScheduleT> selectAllInfoContainsBySupperNo(@Param("exportDate") String mingDate, @Param("strList") List<String> strList);

说明:

mapper中用的@Param注解  此处要和XML中的 collection中的相同,即都是"strList",而foreach循环中的item = “supperNo” ,集合里面的单个值,给下面  #{supperNo } 用,index = "" ,这个是遍历的下标,open  separator  close  这3个比较好理解,就是  ( , , ,) 这样子,拼接括号,中间逗号隔开的意思。

另外两种方式,暂时还没用到,参考网上的,此处记录下来:

3. search(Integer[] ids,String title) 传入参数为多个类型的查询条件时

Map<String, Object> params = new HashMap<String, Object>();
params.put("title", title);
params.put("ids", ids);
<foreach item="id" index="index" collection="ids"  open="(" separator="," close=")">  
         #{id}               
 </foreach>


4.search(Person person) 传入参数为bean对象

 <foreach item="id" index="index" collection="person.ids"  open="(" separator="," close=")">  
         #{id}               
 </foreach>


Oracle数据库使用mybatis的foreach标签应注意的问题(新增)

使用mybatis做数据持久化操作的时候,遇到一个问题,基于oracle数据库做insert操作时,如果使用mybatis的foreach标签,会报错,原来错误的insert语句如下:

<insert id="addChatListRecords" parameterType="ArrayList">
    insert into HELP_CHAT_LIST_T
    (LINK_ID, FROM_USER, TO_USER, FROM_WINDOW, TO_WINDOW, UNREAD, LIST_STATUS, CREATE_DATE, FIELD1, FIELD2)
     values
    <foreach collection="helpChatLists" index="index" separator="," item="item">
      (#{item.linkId,jdbcType=VARCHAR}, #{item.fromUser,jdbcType=VARCHAR},
      #{item.toUser,jdbcType=VARCHAR}, #{item.fromWindow,jdbcType=VARCHAR}, #{item.toWindow,jdbcType=VARCHAR},
      #{item.unread,jdbcType=DECIMAL}, #{item.listStatus,jdbcType=VARCHAR}, #{item.createDate,jdbcType=TIMESTAMP},
      #{item.field1,jdbcType=VARCHAR}, #{item.field2,jdbcType=VARCHAR})
    </foreach>
</insert>

执行之后,报错:“sql未正确结束”,查阅相关资料以后,发现oracle数据库不支持原生的foreach操作,修改之后正确的语句如下:

<insert id="addChatListRecords" parameterType="ArrayList">
      insert into HELP_CHAT_LIST_T
          (LINK_ID, FROM_USER, TO_USER, FROM_WINDOW, TO_WINDOW, UNREAD, LIST_STATUS, CREATE_DATE, FIELD1, FIELD2)
      select t.* from(
      <foreach collection="helpChatLists" item="item" separator="union all">
        select
        #{item.linkId,jdbcType=VARCHAR}, #{item.fromUser,jdbcType=VARCHAR},
        #{item.toUser,jdbcType=VARCHAR}, #{item.fromWindow,jdbcType=VARCHAR}, #{item.toWindow,jdbcType=VARCHAR},
        #{item.unread,jdbcType=DECIMAL}, #{item.listStatus,jdbcType=VARCHAR}, #{item.createDate,jdbcType=TIMESTAMP},
        #{item.field1,jdbcType=VARCHAR}, #{item.field2,jdbcType=VARCHAR}
        from dual
      </foreach>
      ) t
</insert>

猜你喜欢

转载自blog.csdn.net/leaf__yang/article/details/124939736
今日推荐