Mybatis 使用foreach批量插入时,oracle和mysql的不同

一、关于 mybatis foreach标签

mybatis中foreach的主要用在构建in条件中,它可以在SQL语句中进行迭代一个集合。

foreach标签的属性主要有 item,index,collection,open,separator,close

item表示集合中每一个元素进行迭代时的别名,index指定一个名字,用于表示在迭代过程中,每次迭代到的位置,open表示该语句以什么开始,separator表示在每次进行迭代之间以什么符号作为分隔 符,close表示以什么结束,在使用foreach的时候最关键的也是最容易出错的就是collection属性,该属性是必须指定的,但是在不同情况 下,该属性的值是不一样的,主要有一下3种情况:

  • 如果传入的是单参数且参数类型是一个List的时候,collection属性值为list
  • 如果传入的是单参数且参数类型是一个array数组的时候,collection的属性值为array
  • 如果传入的参数是多个的时候,我们就需要把它们封装成一个Map了,当然单参数也可以封装成map

使用批量插入执行的SQL语句应该等价于:

 insert into redeem_code (batch_id, code, type, facevalue,create_user,create_time)
 values
 (?,?,?,?,?,? ),(?,?,?,?,?,? ),(?,?,?,?,?,? ),(?,?,?,?,?,? )

二、oracle和mysql中使用foreach的不同

Mybatis使用foreach批量插入的时候,针对不同的数据库,写法也是不一样的,很多习惯了mysql写法的同学,在换库到oracle的时候会踩到这些坑。

主要不同点在于foreach标签内separator属性的设置问题

  • mysql:separator设置为","分割时,最终拼接的代码形式为:insert into table_name (a,b,c) values (v1,v2,v3) ,(v4,v5,v6) ,...
  • oracle:separator设置为"union all"分割时,最终拼接的代码形式为:insert into table_name (a,b,c) values (v1,v2,v3) union all (v4,v5,v6) union all...

代码如下,

1、mysql

separator设置为","分割,

<insert id="insertBatchUser" parameterType="com.test.User">
    insert into table_name (name, adress, age)
        values
        <foreach collection="list" item="item" index="index" separator=",">
            (   #{item.name},  #{item.adress},  #{item.age}  )
        </foreach>
</insert>

2、oracle

separator设置为"union all"分割,并且参数使用 select .... from dual

<insert id="insertBatchUser" parameterType="com.test.User">
    insert into table_name (name, adress, age)
        values
        <foreach collection="list" item="item" index="index" separator="union all">
            (select #{item.name}, 
                    #{item.adress}, 
                    #{item.age} 
                from dual   )
        </foreach>
</insert>
发布了144 篇原创文章 · 获赞 146 · 访问量 6万+

猜你喜欢

转载自blog.csdn.net/shipfei_csdn/article/details/104625607