【性能优化】Mybatis Plus:优化查询速度 - SQL替换Service

优化查询速度 - SQL替换Service

Service 接口问题

下面是原先的 Service 实现类代码,有门店 ID、订单状态、查询时间段,然后查出了所有的结果,继续使用 java8 的特性获取汇总结果,随着项目的推移,数据量越来越大,这种方式是不可取的,随便都能上几十秒查不出来,导致请求超时,下面我们就来优化一下这个方法
在这里插入图片描述

SQL 优化

先把上面的方法都转换成 SQL 语句的写法,得到下面的 5 个查询 SQL

select sum(A.pay_money) originPrice, count(A.id) countOrder, sum(A.pay_money) payMoney
from biz_order_info A
where A.`status` = 1 and A.order_status = 2 and A.store_id = 1;

select sum(A.pay_money) smPayMoney
from biz_order_info A
where A.`status` = 1 and A.order_status = 2 and A.store_id = 1 and A.pay_way = 1;

select sum(A.pay_money) rlPayMoney
from biz_order_info A
where A.`status` = 1 and A.order_status = 2 and A.store_id = 1 and A.pay_way = 2;

select sum(A.pay_money) sjPayMoney
from biz_order_info A
where A.`status` = 1 and A.order_status = 2 and A.store_id = 1 and A.pay_way = 3;

select sum(A.pay_money) xjPayMoney
from biz_order_info A
where A.`status` = 1 and A.order_status = 2 and A.store_id = 1 and A.pay_way = 4;

整理一下代码,通过union all连接,最简单的方法,后端使用 List 来接收返回值,有一定的可行性

select * from (
	(select sum(A.pay_money) 'value' from biz_order_info A where A.`status` = 1 and A.order_status = 2 and A.store_id = 1)
	union all
	(select count(A.id) 'value' from biz_order_info A where A.`status` = 1 and A.order_status = 2 and A.store_id = 1)
	union all
	(select sum(A.pay_money) 'value' from biz_order_info A where A.`status` = 1 and A.order_status = 2 and A.store_id = 1)
	union all
	(select sum(A.pay_money) 'value' from biz_order_info A where A.`status` = 1 and A.order_status = 2 and A.store_id = 1 and A.pay_way = 1)
	union all
	(select sum(A.pay_money) 'value' from biz_order_info A where A.`status` = 1 and A.order_status = 2 and A.store_id = 1 and A.pay_way = 2)
	union all
	(select sum(A.pay_money) 'value' from biz_order_info A where A.`status` = 1 and A.order_status = 2 and A.store_id = 1 and A.pay_way = 3)
	union all
	(select sum(A.pay_money) 'value' from biz_order_info A where A.`status` = 1 and A.order_status = 2 and A.store_id = 1 and A.pay_way = 4)
) X;

查询结果
在这里插入图片描述
当我放到项目中时,发现还有查询条件,时间段,如果上面的 SQL 加上时间段,将会变的非常臃肿且难维护,所以上面的 SQL 报废了,不能使用,继续优化 SQL

-- 最开始的SQL
select A.*
from biz_order_info A
where A.`status` = 1 and A.order_status = 2;

-- 初步汇总,拿到3个我们需要的值
select sum(A.pay_money), count(A.id), sum(A.pay_money)
from biz_order_info A
where A.`status` = 1 and A.order_status = 2;

问题来了,怎么在已经查询出的结果中分支付方式汇总数据?

这里我使用的是 sum + case when 结构,分类汇总数据,再次优化 SQL

select sum(A.pay_money) originPrice, count(A.id) countOrder, sum(A.pay_money) payMoney,
sum(case A.pay_way when '1' THEN A.pay_money ELSE 0 END) smPayMoney,
sum(case A.pay_way when '2' THEN A.pay_money ELSE 0 END) rlPayMoney,
sum(case A.pay_way when '3' THEN A.pay_money ELSE 0 END) sjPayMoney,
sum(case A.pay_way when '4' THEN A.pay_money ELSE 0 END) xjPayMoney
from biz_order_info A
where A.`status` = 1 and A.order_status = 2

查询结果
在这里插入图片描述
接下来随便一试,有两种方式处理业务逻辑了

  • 方法一:后台使用 Vo 实体类直接接收
  • 方法二:使用 Map 接收

下面是测试结果,Service 操作性能提升了 75.61% ,所以以后不要查询所有的数据!!!
在这里插入图片描述
优化后的接口
在这里插入图片描述

不要一次性查询所有表数据 一次性 SQL 解决的问题,就不要写 Service 方法了

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Mybatis-plus是MyBatis增强工具包,用于简化CRUD操作。该工具包为MyBatis提供了一些高效,有用,即用的功能,使用它可以有效地节省您的开发时间。 Mybatis-plus特征: 与MyBatis完全兼容 启动时自动配置 开箱即用的用于操作数据库的界面 强大而灵活的条件包装器 生成主键的多种策略 Lambda样式的API 全能和高度可定制的代码生成器 自动分页操作 SQL注入防御 支持活动记录 支持可插拔的自定义界面 内置许多有用的扩展 Mybatis-plus功能: 1、单表CURD(简单 + 批量)操作,自动完成(支持 like 比较等查询)。 2、分页插件,Count查询自动或自定义SQL查询。 3、Spring根据不同环境加载不同配置支持(支持typeAliasesPackage通配符扫描)。 【自动生成Entity  Mapper  Service文件】 Mybatis-plus更新日志: v3.4.3 增加瀚高数据库支持 增加注解 Order By 支持默认排序 Wrapper exists notExists orderBy groupBy 支持参数绑定 Wrapper 支持 setParamAlias 其它优化 优化 KeyGenerator 支持多实现多数据源注入 增强 ServiceImpl 泛型推断,解决多继承与代理问题 新增 PageDto 用于微服务对象传输序列化 新增 Page 提供静态 of 构造方式 增加代理 MethodHandleProxies 对 lambda 调试支持 调整 ActiveRecord 日志对象初始化 调整 ActiveRecord 模式 Model 类开发 pkVal 方法外部可用 删除标记过时代码 优化枚举值获取方式 分页 count 安全处理 Sequence 方法支持重写支持 升级 Mybatis 3.5.7 修复自动配置 lazy-initialization 无属性提示 修复 mysql on duplicate key update 字段名判断为表名问题 修复 lambda 条件 npe 异常 重构 lambda 信息提取方法 获取 lambda 信息不在序列化 合并 gitee pulls/ 141 fixed github issues/3208 3016 fixed github issues/3482 数据权限处理器支持 union all 调整事务未启用打印提示信息 单元测试优化相关依赖升级
假设你使用的是mybatis-plus框架,同时也已经实现了查询两条数据并将这两条数据中的`department`字段相互替换的逻辑,那么接下来你可以使用mybatis-plus提供的`UpdateWrapper`类来更新表数据。 首先,你需要将查询出来的两条记录中的`department`字段相互替换,然后将这两条记录的`id`值保存到一个列表中,如下所示: ```java List<Map<String,Object>> resultList = ...; String department1 = null; String department2 = null; List<Long> idList = new ArrayList<>(); for (Map<String,Object> map : resultList) { if (map.get("id").equals(id1)) { department1 = (String)map.get("department"); idList.add(id1); } else if (map.get("id").equals(id2)) { department2 = (String)map.get("department"); idList.add(id2); } } ``` 接下来,你可以使用`UpdateWrapper`类来构造更新条件,并调用`update`方法来更新表数据。具体代码如下: ```java UpdateWrapper wrapper = new UpdateWrapper(); wrapper.in("id", idList); wrapper.set("department", department1, SqlKeyword.EQUALS, department2); employeeMapper.update(null, wrapper); ``` 上面的代码中,我们先构造了一个`UpdateWrapper`对象,其中使用了`in`方法来设置更新条件,只更新`id`值在`idList`中的记录。然后,我们使用`set`方法来设置需要更新的字段和对应的值,注意使用了`SqlKeyword.EQUALS`来表示对应的值需要相互替换。最后,我们调用了`update`方法来执行更新操作,并将`UpdateWrapper`对象作为第一个参数传递给`update`方法,表示更新条件。`null`表示不设置更新的实体对象。 需要注意的是,上面的代码中,`employeeMapper`是一个mybatis-plus生成的Mapper类,你需要根据自己的实际情况来替换。同时,为了保证代码的可读性和可维护性,你可能需要将上面的代码封装成一个Service方法来使用。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值