SQL_CALC_FOUND_ROWS 和 FOUND_ROWS()实现对复杂sql实现分页与总条数查询

发布于:2024-06-20 ⋅ 阅读:(176) ⋅ 点赞:(0)

需求

ReturnResult result = new ReturnResult();
try {
	List<Map> forList = (List<Map>) dao.findForList("Mapper.getList", map);
	int count = (int) dao.findForObject("Mapper.getCount", map);
	result.setData(forList);
	result.setCode(0);
	result.setFlag(true);
	result.setCount(count);
} catch (Exception e) {
	result.setCode(0);
	result.setMessage(e.getMessage());
	result.setFlag(false);
}
return result;

以上代码运行速度缓慢,当数据量过大时,运行时间超过20秒。优化运行速度。

思路

这段代码看起来逻辑非常简通过dao调用了两次Mapper中的SQL语句,第一次通过map将条件及页码传入,查询出对应页码的数据。
第二次将sql中的limit去除,实现查询全部数据。
首先使用explain查看语句是否走索引。经测试sql有部分条件没有索引,将索引添加完毕后速度有了质的提高。
但查看sql语句,发现两段调用sql几乎相同,运行时间也相同,java程序顺序执行,及执行时间翻倍。使用SQL_CALC_FOUND_ROWSFOUND_ROWS()可以解决该问题。

使用及完整代码

利用 SQL_CALC_FOUND_ROWSFOUND_ROWS()关键字。以下是具体的 SQL 查询方法:

  1. 使用 SQL_CALC_FOUND_ROWSSQL 查询

    SELECT SQL_CALC_FOUND_ROWS *
    FROM table
    WHERE 查询条件
    LIMIT 页码, 条数;
    

·*·代表需要查询出的字段。
2. 使用FOUND_ROWS()获取总条数

   SELECT FOUND_ROWS();

SQL_CALC_FOUND_ROWS 会计算符合条件的总行数,而不受 LIMIT 的影响。FOUND_ROWS() 会返回上一个查询的结果总数。

Java 代码实现

ReturnResult result = new ReturnResult();
try {
    // 获取分页数据
    List<Map> forList = (List<Map>) dao.findForList("Mapper.getList", map);
    // 获取总条数
    int count = (int) dao.findForObject("Mapper.getCount");
    result.setData(forList);
    result.setCode(0);
    result.setFlag(true);
    result.setCount(count);
} catch (Exception e) {
    result.setCode(0);
    result.setMessage(e.getMessage());
    result.setFlag(false);
}
return result;

Mapper XML

<!-- 获取分页数据并计算总条数 -->
<select id="getList" parameterType="map" resultType="map">
   SELECT SQL_CALC_FOUND_ROWS *
   FROM table
   WHERE 查询条件
   LIMIT 页码, 条数;
</select>

<!-- 获取总条数 -->
<select id="getCount" resultType="int">
    SELECT FOUND_ROWS();
</select>

网站公告

今日签到

点亮在社区的每一天
去签到