MyBatis批量插入——常见错误

首先看我写的垃圾代码,有多少出错误 

    <insert id="addStudents" parameterType="java.util.List">
        insert into student(STU_NUMBER,STU_NAME,STU_SEX,PROFESSION_CODE)
        values
        <foreach collection="students" item="student" index="index" separator=",">
            (
            <if test="stuNumber!=null and stuNumber!=''">
                STU_NUMBER = #{student.stuNumber},
            </if>
            <if test="stuName!=null and stuName!=''">
                STU_NAME = #{student.stuName},
            </if>
            <if test="stuSex!=null and stuSex!=''">
                STU_SEX = #{student.stuSex},
            </if>
            <if test="professionCode!=null and professionCode!=''">
                PROFESSION_CODE = #{student.professionCode}
            </if>
            )
        </foreach>
    </insert>

看不出来没关系,下边有参数解释: 

foreach的主要作用在构建in条件中,它可以在SQL语句中进行迭代一个集合。foreach元素的属性主要有 collection,item,separator,index,open,close。

  1. collection:指定要遍历的集合。表示传入过来的参数的数据类型。该属性是必须指定的,要做 foreach 的对象。在使用foreach的时候最关键的也是最容易出错的就是collection属性。在不同情况 下,该属性的值是不一样的,主要有一下3种情况:
    a. 如果传入的是单参数且参数类型是一个List的时候,collection属性值为list
    b. 如果传入的是单参数且参数类型是一个array数组的时候,collection的属性值为array
    c. 如果传入的参数是多个的时候,我们就需要把它们封装成一个Map了,当然单参数也可以封装成map。Map 对象没有默认的键

  2. item:表示集合中每一个元素进行迭代时的别名。将当前遍历出的元素赋值给指定的变量,然后用#{变量名},就能取出变量的值,也就是当前遍历出的元素。

  3. separator:表示在每次进行迭代之间以什么符号作为分隔符。select * from tab where id in(1,2,3)相当于1,2,3之间的","

  4. index:索引。index指定一个名字,用于表示在迭代过程中,每次迭代到的位置。遍历list的时候index就是索引,遍历map的时候index表示的就是map的key,item就是map的值。

  5. open表示该语句以什么开始,close表示以什么结束。

 1、参数类型是list,但写collection参数时我写了个students,错误!这里传参是list类型,直接写list就行。

如果是传如多个值,比如有条件的批量修改时,有多个参数,传参肯定是Map,这时候你可以在参数Map里边放list,如:map.put("listName",list),此时对应collection参数要写你往Map里放的listName。

修改一下,再往下看:

    <insert id="addStudents" parameterType="java.util.List">
        insert into student(STU_NUMBER,STU_NAME,STU_SEX,PROFESSION_CODE)
        values
        <foreach collection="list" item="student" index="index" separator=",">
            (
            <if test="stuNumber!=null and stuNumber!=''">
                STU_NUMBER = #{student.stuNumber},
            </if>
            <if test="stuName!=null and stuName!=''">
                STU_NAME = #{student.stuName},
            </if>
            <if test="stuSex!=null and stuSex!=''">
                STU_SEX = #{student.stuSex},
            </if>
            <if test="professionCode!=null and professionCode!=''">
                PROFESSION_CODE = #{student.professionCode}
            </if>
            )
        </foreach>
    </insert>

2、判断参数值是否为空,test内容错误,至少要加上“student.”吧。测试运行项目,其他地方正常的话,这里会报错,报错信息如下:存储的数据与数据库表的字段类型定义不相匹配

Column count doesn't match value count at row 1

sql代码实际上是这样:

insert into student(STU_NUMBER,STU_NAME,STU_SEX,PROFESSION_CODE)
        values (),()...

因为test判断时都为空 ,下边语句也不会执行,因此也不可能获取到值,实际上在这里不需要做非空判断了,因为一旦有空值,就会导致前边插入列数与后边值数不匹配,

insert into student(STU_NUMBER,STU_NAME,STU_SEX,PROFESSION_CODE)
        values (value1,value2,value4),(value1,value3,value4)...

还会报Column count doesn't match value count at row 1错误,如果有必要在java代码做判断比较好

修改一下,再往下看:

    <insert id="addStudents" parameterType="java.util.List">
        insert into student(STU_NUMBER,STU_NAME,STU_SEX,PROFESSION_CODE)
        values
        <foreach collection="list" item="student" index="index" separator=",">
            (
            STU_NUMBER = #{student.stuNumber},
            STU_NAME = #{student.stuName},
            STU_SEX = #{student.stuSex},
            PROFESSION_CODE = #{student.professionCode}
            )
        </foreach>
    </insert>

3、这时候运行,应该不会报错,但是插入数据库的值全为NULL,因为Value()里面直接给值就行,不需要再写XX = #{xx}了。

    <insert id="addStudents" parameterType="java.util.List">
        insert into student(STU_NUMBER,STU_NAME,STU_SEX,PROFESSION_CODE)
        values
        <foreach collection="list" item="student" index="index" separator=",">
            (
            #{student.stuNumber},
            #{student.stuName},
            #{student.stuSex},
            #{student.professionCode}
            )
        </foreach>
    </insert>

这样就正常了。

写个代码写的如痴如醉,一塌糊涂。

参考博客及问答:

https://www.cnblogs.com/yizhiamumu/p/9044523.html

https://www.iteye.com/blog/msq-141634

http://www.imooc.com/article/details/id/284701

https://ask.csdn.net/questions/358801?sort=id

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值