广告位联系
返回顶部
分享到

mybatis解决<foreach>标签不能超过1000的问题

java 来源:互联网 作者:佚名 发布时间:2024-05-01 22:00:39 人浏览
摘要

错误写法: 1 2 3 4 5 6 7 8 select id=getProductInfoList resultType=vo select a.name from A a where a.idin foreach collection=ids item=item index=index open=( close=) separator=, #{item} /foreach /select 错误原因: 当foreach标签内的数量

错误写法:

1

2

3

4

5

6

7

8

<select id="getProductInfoList" resultType="vo">

    select a.name

    from A a

    where a.idin

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

        #{item}

    </foreach>

</select>

错误原因:

当<foreach>标签内的数量超过1000个时会提示一下报错:

1

java.sql.SQLSyntaxErrorException: ORA-01795: maximum number of expressions in a list is 1000

正确写法:

方案1(将传参变成SQL语句嵌套在SQL里面):

1

2

3

4

5

6

<select id="getProductInfoList" resultType="vo">

    select a.name

    from A a

    where a.id in

     (select b.id from B b where b.id = #{billNo}  and DELETED = 0)

</select>

方案2(利用or每1000条添加一个or)

1

2

3

4

5

6

7

8

9

SELECT

    *

FROM

    ${tabNameMx} M

    WHERE

    M.CODE_ID IN

    <foreach collection="idList" index="index" open="(" close=")" item="id" separator=",">

        <if test="(index % 999) == 998"> NULL) OR M.CODE_ID IN(</if>#{id}

    </foreach>

这个SQL大家看着可能觉得有点懵逼,现在给你写段这段sql最终会变成什么样子,这样你瞬间就懂了。

SQL最终执行的样子:

1

CODE_ID IN('......','998',NULL ) OR M.CODE_ID IN('999',.....  NULL) OR M.CODE_ID IN('.....')

方案3(拼接OR ID IN ()):

1

2

3

4

5

6

7

8

9

10

11

12

13

14

<select id="queryEnoByCapita">

  select t.custid,to_char(t.eno) as eno from T_E_ACCOUNT t where t.status !='2' and   t.custid in

 <trim suffixOverrides=" OR t.custid in()">

 <foreach collection="capita" item="custId" index="index" open="(" close=")">  

            <if test="index != 0">

                <choose>

                    <when test="index % 1000 == 999">) OR t.custid in (</when>

                    <otherwise>,</otherwise>

                </choose>

            </if>

     #{custId,jdbcType=VARCHAR}

 </foreach>

 </trim>

</select>

分析:

1

2

3

4

5

6

<trim>标签suffixOverrides:去掉后缀匹配上的东西,本例中后缀如果是 OR t.custid in()与suffixOverrides的属性值刚好匹配,则去掉 OR t.custid in()

  

index 集合迭代的位置从0开始,为何需要<if test="index != 0">?如果没有,则sql是 t.cust in (,1,2..)会多一个逗号

  

没有999条数据的拼接SQL为:t.cust in (1,2..998)

超过999条的数据拼接SQL为:t.cust in (1,2..998) or t.custid in(999,1000...1998) ...

拓展:

扩展1:foreach元素的属性主要有 item、index、 collection、open、separator、close

1

2

3

4

5

6

collection  foreach循环的对象

item 集合中每一个元素或者该集合的对象,支持对象点属性的方式获取属性#{obj.filed} 或#{value}

index 循环的下标,从0开始

open 表示以什么开始

separator 每次进行迭代之间以什么符号作为分隔符

close表示以什么结束

扩展2:MyBatis trim 标签四个属性和其作用

1

2

3

4

prefix  添加前缀

prefixOverrides  删除前缀

suffix  添加后缀

suffixOverrides  删除后缀


版权声明 : 本文内容来源于互联网或用户自行发布贡献,该文观点仅代表原作者本人。本站仅提供信息存储空间服务和不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权, 违法违规的内容, 请发送邮件至2530232025#qq.cn(#换@)举报,一经查实,本站将立刻删除。
原文链接 :
相关文章
  • 本站所有内容来源于互联网或用户自行发布,本站仅提供信息存储空间服务,不拥有版权,不承担法律责任。如有侵犯您的权益,请您联系站长处理!
  • Copyright © 2017-2022 F11.CN All Rights Reserved. F11站长开发者网 版权所有 | 苏ICP备2022031554号-1 | 51LA统计