• 设为首页
  • 收藏本站
  • 积分充值
  • VIP赞助
  • 手机版
  • 微博
  • 微信
    微信公众号 添加方式:
    1:搜索微信号(888888
    2:扫描左侧二维码
  • 快捷导航
    福建二哥 门户 查看主题

    复杂SQL实现分组分情况分页查询代码实例

    发布者: 山止川行 | 发布时间: 2025-6-20 09:09| 查看数: 107| 评论数: 0|帖子模式

    前言

    在处理数据库查询时,分页是一个常见的需求。
    尤其是在处理大量数据时,一次性返回所有结果可能会导致性能问题。
    因此,我们需要使用分页查询来限制返回的结果数量。同时,根据特定的条件筛选数据也是非常常见的需求。
    在本博客中,我们将探讨如何根据 camp_status 字段分为 6 种情况进行分页查询,并根据  camp_type 字段区分活动类型,返回不同的字段。
    我们将使用 SQL 变量来实现这一功能,并通过示例进行详细解释。

    一、根据 camp_status 字段分为 6 种情况


    1.1 SQL语句

    要将分页结果按 6 种情况来区分。
    SQL如下:
    1. SELECT         count(*)                                                                 AS allCampCount,
    2.                SUM(CASE WHEN CAMP_STATUS IN ('31', '32', '35', '55') THEN 1 ELSE 0 END) AS approvalCampCount,
    3.                SUM(CASE WHEN CAMP_STATUS IN ('40', '41', '56') THEN 1 ELSE 0 END)       AS toExecuteCampCount,
    4.                SUM(CASE WHEN CAMP_STATUS IN ('42', '66', '67') THEN 1 ELSE 0 END)       AS executeCampCount,
    5.                SUM(CASE WHEN CAMP_STATUS IN ('50', '60') THEN 1 ELSE 0 END)             AS completeCampCount,
    6.                SUM(CASE WHEN CAMP_STATUS IN ('30') THEN 1 ELSE 0 END)                   AS overruleCampCount
    7.         FROM BMA_MARKET_CAMP
    8.         WHERE USER_ID = #{userId}
    复制代码
    1.2 SQL解释

    这是一个SQL查询,用于从名为
    1. BMA_MARKET_CAMP
    复制代码
    的表中选择和计算数据。下面是对这个查询的逐行解释:

      1. SELECT count(*) AS allCampCount
      复制代码
      : 这一行计算了
      1. BMA_MARKET_CAMP
      复制代码
      表中的总记录数,并将这个数量命名为
      1. allCampCount
      复制代码

      1. SUM(CASE WHEN CAMP_STATUS IN ('31', '32', '35', '55') THEN 1 ELSE 0 END) AS approvalCampCount
      复制代码
      : 这一行计算了
      1. CAMP_STATUS
      复制代码
      字段值为'31', '32', '35', 或 '55'的总数,并将这个数量命名为
      1. approvalCampCount
      复制代码
      。这些状态可能是表示“待批准”或“正在批准”的状态代码。
      1. SUM(CASE WHEN CAMP_STATUS IN ('40', '41', '56') THEN 1 ELSE 0 END) AS toExecuteCampCount
      复制代码
      : 这一行计算了
      1. CAMP_STATUS
      复制代码
      字段值为'40', '41', 或 '56'的总数,并将这个数量命名为
      1. toExecuteCampCount
      复制代码
      。这些状态可能是表示“待执行”或“即将执行”的状态代码。
      1. SUM(CASE WHEN CAMP_STATUS IN ('42', '66', '67') THEN 1 ELSE 0 END) AS executeCampCount
      复制代码
      : 这一行计算了
      1. CAMP_STATUS
      复制代码
      字段值为'42', '66', 或 '67'的总数,并将这个数量命名为
      1. executeCampCount
      复制代码
      。这些状态可能是表示“正在执行”或“已执行”的状态代码。
      1. SUM(CASE WHEN CAMP_STATUS IN ('50', '60') THEN 1 ELSE 0 END) AS completeCampCount
      复制代码
      : 这一行计算了
      1. CAMP_STATUS
      复制代码
      字段值为'50'或'60'的总数,并将这个数量命名为
      1. completeCampCount
      复制代码
      。这些状态可能是表示“已完成”或“完全完成”的状态代码。
      1. SUM(CASE WHEN CAMP_STATUS IN ('30') THEN 1 ELSE 0 END) AS overruleCampCount
      复制代码
      : 这一行计算了
      1. CAMP_STATUS
      复制代码
      字段值为'30'的总数,并将这个数量命名为
      1. overruleCampCount
      复制代码
      。这个状态可能是表示“已否决”或“推翻”的状态代码。
      1. FROM BMA_MARKET_CAMP WHERE USER_ID = #{userId}
      复制代码
      : 最后,指定了数据来源的表是
      1. BMA_MARKET_CAMP
      复制代码
      ,并且只选择那些
      1. USER_ID
      复制代码
      字段等于给定参数
      1. #{userId}
      复制代码
      的记录。
    总的来说,这个查询是为了获取与特定用户相关的各种 camp 状态的数量。

    二、分页 SQL 实现


    2.1 SQL语句

    这是整个 SQL 语句,下面会细细讲解!
    SQL如下:
    1.         SELECT TOUCH_TYPE,
    2.                t1.CAMP_TYPE,
    3.                NAME,
    4.                SMS_CONTENT,
    5.                CASE
    6.                    WHEN t1.CAMP_TYPE = '0' THEN
    7.                        NULL
    8.                    ELSE
    9.                        START_DATE END AS START_DATE,
    10.                CASE
    11.                    WHEN t1.CAMP_TYPE = '0' THEN
    12.                        EXE_START_TIME
    13.                    ELSE
    14.                        START_TIME END AS START_TIME,
    15.                CASE
    16.                    WHEN t1.CAMP_TYPE = '0' THEN
    17.                        NULL
    18.                    ELSE
    19.                        END_DATE END   AS END_DATE,
    20.                CASE
    21.                    WHEN t1.CAMP_TYPE = '0' THEN
    22.                        NULL
    23.                    ELSE
    24.                        END_TIME END   AS END_TIME
    25.         FROM CAMP t1
    26.                  left join CAMP_INFO t2 on t1.ID = t2.CAMP_ID
    27.         WHERE CAMP_STATUS  in
    28.         <foreach close=")" collection="campStatus" item="campStatus" open="(" separator=", ">
    29.             #{campStatus,jdbcType=VARCHAR}
    30.         </foreach>
    31.           AND USER_ID = #{userId}
    复制代码
    2.2 根据 camp_type 区分返回字段


    • 当活动类型为 0 时,只需要返回 EXE_STRAR_TIME 字段。
    • 其他的活动类型要返回 START_DATE , START_TIME , END_DATE , END_TIME 四个字段。
    SQL部分如下:
    1.                CASE
    2.                    WHEN t1.CAMP_TYPE = '0' THEN
    3.                        NULL
    4.                    ELSE
    5.                        START_DATE END AS START_DATE,
    6.                CASE
    7.                    WHEN t1.CAMP_TYPE = '0' THEN
    8.                        EXE_START_TIME
    9.                    ELSE
    10.                        START_TIME END AS START_TIME,
    11.                CASE
    12.                    WHEN t1.CAMP_TYPE = '0' THEN
    13.                        NULL
    14.                    ELSE
    15.                        END_DATE END   AS END_DATE,
    16.                CASE
    17.                    WHEN t1.CAMP_TYPE = '0' THEN
    18.                        NULL
    19.                    ELSE
    20.                        END_TIME END   AS END_TIME
    复制代码
    2.3 根据 camp_status 字段分为 6 种情况

    解释如下:

      1. WHERE CAMP_STATUS in
      复制代码
      : 这表示我们要在SQL查询中添加一个条件,即
      1. CAMP_STATUS
      复制代码
      的值必须在给定的列表中。
      1. <foreach ...>
      复制代码
      : 这是MyBatis的循环语句,用于遍历集合或数组,并动态生成SQL的部分内容。
      1. collection="campStatus"
      复制代码
      : 这表示我们要遍历的集合或数组的名称是
      1. campStatus
      复制代码

      1. item="campStatus"
      复制代码
      : 在每次循环中,当前的元素值会被赋值给名为
      1. campStatus
      复制代码
      的变量。
      1. open="("
      复制代码
      1. close=")"
      复制代码
      : 这些指示MyBatis在循环开始前添加一个左括号
      1. (
      复制代码
      ,并在循环结束后添加一个右括号
      1. )
      复制代码

      1. separator=", ">: 这表示在每次循环后,我们添加一个逗号
      复制代码
      ,`和一个空格。
      1. #{campStatus,jdbcType=VARCHAR}
      复制代码
      : 这是MyBatis的参数占位符。它表示我们要将当前循环中的
      1. campStatus
      复制代码
      变量的值插入到SQL查询中。
      1. jdbcType=VARCHAR
      复制代码
      指定了参数的类型,这里假设它是VARCHAR类型。
    综上所述,这个片段的作用是动态生成一个SQL查询的条件,该条件检查
    1. CAMP_STATUS
    复制代码
    是否在给定的
    1. campStatus
    复制代码
    列表中。
    SQL部分如下:
    1.         SELECT
    2.             ...

    3.         FROM
    4.             ...
    5.         WHERE CAMP_STATUS  in
    6.         <foreach close=")" collection="campStatus" item="campStatus" open="(" separator=", ">
    7.             #{campStatus,jdbcType=VARCHAR}
    8.         </foreach>
    9.         ...
    复制代码
    这里传入的是一个 list,这样传入即可:

    定义一个请求类:
    1. @Data
    2. public class CampDataInfoInIndexRequest {
    3.     List<Integer> campStatusList;
    4.     private int pageNum;
    5.     private int pageSize;
    6. }
    复制代码
    三、分页实现

    实现一个 PageUtils 。
    代码如下:
    1. public class PageUtils {
    2.     /**
    3.      * 泛型方法 进行结果的分页
    4.      * 当pageNum*pageSize>result.size那么就取result的最后一页数据
    5.      * 否则就取相应页的数据
    6.      *
    7.      * @param result
    8.      * @param pageNum
    9.      * @param pageSize
    10.      * @return
    11.      */
    12.     public static <T> List<T> pageResult(List<T> result, Integer pageNum, Integer pageSize) {
    13.         if (Objects.isNull(result) || result.size() == 0) {
    14.             return result;
    15.         }
    16.         int maxSize = result.size();
    17.         if (maxSize < pageNum * pageSize + pageSize) {
    18.             int maxPage = maxSize / pageSize;
    19.             return result.subList(maxPage * pageSize, result.size());
    20.         }
    21.         return result.subList(pageNum * pageSize, (pageNum + 1) * pageSize);
    22.     }
    23. }
    复制代码
    再通过一个 PageResultVO 返回即可。
    代码如下:
    1. @Data
    2. public class PageResultVO {
    3.     private Integer total;
    4.     private List<?> list;
    5. }



    6. //ServiceImpl层
    7. List<CampInfoVO> infoList = PageUtils.pageResult(info, pageNum, pageSize);
    8. PageResultVO pageResultVO = new PageResultVO();
    9. pageResultVO.setTotal(info.size());
    10. pageResultVO.setList(infoList);
    复制代码
    四、总结

    在这篇博客中,我们探讨了如何使用SQL实现分页查询,并根据camp_status和camp_type字段进行筛选。
    通过使用变量和适当的SQL语法,我们可以根据特定的条件动态地构建查询,从而返回满足我们需求的结果。
    通过这种方式,我们可以灵活地构建和执行查询,以满足不同的需求。这对于处理大量数据和实现复杂的筛选条件非常有用。
    到此这篇关于复杂SQL实现分组分情况分页查询的文章就介绍到这了,更多相关复杂SQL分组分页查询内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

    来源:https://www.jb51.net/database/308731hw7.htm
    免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!

    本帖子中包含更多资源

    您需要 登录 才可以下载或查看,没有账号?立即注册

    ×

    最新评论

    浏览过的版块

    QQ Archiver 手机版 小黑屋 福建二哥 ( 闽ICP备2022004717号|闽公网安备35052402000345号 )

    Powered by Discuz! X3.5 © 2001-2023

    快速回复 返回顶部 返回列表