MySQL SQL 优化案例:JOIN派生表
来源:互联网 发布:mac唇膏试色最全 编辑:程序博客网 时间:2024/04/27 13:37
优化之前:
SELECT ap.institution_id, date(ra.create_time) date, sum( IF ( ra.confirm_amount > ld.debit_amount, ld.debit_amount, ra.confirm_amount ) ) return_amount, count(ra.confirm_amount) return_countFROM t_asset_package apJOIN ( SELECT asset_package_id, institution_id, loan_document_id, debit_amount FROM t_loan_details WHERE is_all_paid = 1 OR principal_paid = 1) ld ON ap.asset_package_id = ld.asset_package_idJOIN ( SELECT loan_document_id, sum(confirm_amount) confirm_amount, create_time FROM t_return_application GROUP BY loan_document_id) ra ON ld.loan_document_id = ra.loan_document_idWHERE ap.institution_id = 'C0000012413'AND ap.delete_flag = 0GROUP BY date(ra.create_time)ORDER BY date;
执行计划:
+----+-------------+----------------------+--------+-----------------------------------------+--------------------------------------+---------+---------------------+--------+---------------------------------+| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |+----+-------------+----------------------+--------+-----------------------------------------+--------------------------------------+---------+---------------------+--------+---------------------------------+| 1 | PRIMARY | <derived3> | ALL | NULL | NULL | NULL | NULL | 89435 | Using temporary; Using filesort || 1 | PRIMARY | <derived2> | ALL | NULL | NULL | NULL | NULL | 88516 | Using where; Using join buffer || 1 | PRIMARY | ap | eq_ref | PRIMARY,FK_ASSET_PACKAGE_CUSTOMER_1_idx | PRIMARY | 110 | ld.asset_package_id | 1 | Using where || 3 | DERIVED | t_return_application | index | NULL | FK_RETURN_APPLICATION_DOCUMENT_1_idx | 111 | NULL | 203837 | || 2 | DERIVED | t_loan_details | ALL | NULL | NULL | NULL | NULL | 99370 | Using where |+----+-------------+----------------------+--------+-----------------------------------------+--------------------------------------+---------+---------------------+--------+---------------------------------+需要执行21分钟
优化思路:之前的SQL连接的是派生表,并不能有效使用到索引,导致这一写法的直接原因是程序员的惯性思维,总以为先把要join的内容通过过滤、分组、聚合限定在一个小的范围内之后再join效率较高且更符合惯常的思维模式。殊不知MySQL这么做会导致很差的性能。要做的优化就是先直接join这样可以利用到join字段上的索引,之后再进行过滤、分组 、聚合。
优化后:
SELECT alr.institution_id, alr.date, SUM( IF ( alr.confirm_amount > alr.debit_amount, alr.debit_amount, alr.confirm_amount ) ) return_amount, count(alr.confirm_amount) return_countFROM ( SELECT ap.institution_id institution_id, DATE(ra.create_time) date, SUM(ra.confirm_amount) confirm_amount, ld.debit_amount debit_amount FROM t_asset_package ap JOIN t_loan_details ld ON ap.asset_package_id = ld.asset_package_id AND ( ld.is_all_paid = 1 OR ld.principal_paid = 1 ) JOIN t_return_application ra ON ld.loan_document_id = ra.loan_document_id WHERE ap.institution_id = 'C0000012413' AND ap.delete_flag = 0 GROUP BY ra.loan_document_id ) alrGROUP BY alr.date
执行计划:
+----+-------------+------------+------+-----------------------------------------------------------+-----------------------------------------+---------+------------------------------+------+----------------------------------------------+| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |+----+-------------+------------+------+-----------------------------------------------------------+-----------------------------------------+---------+------------------------------+------+----------------------------------------------+| 1 | PRIMARY | <derived2> | ALL | NULL | NULL | NULL | NULL | 2 | Using temporary; Using filesort || 2 | DERIVED | ap | ref | PRIMARY,FK_ASSET_PACKAGE_CUSTOMER_1_idx | FK_ASSET_PACKAGE_CUSTOMER_1_idx | 63 | | 3 | Using where; Using temporary; Using filesort || 2 | DERIVED | ld | ref | IDX_LOAN_DOCUMENT,FK_LOAN_FEE_DETAILS_ASSET_PACKAGE_1_idx | FK_LOAN_FEE_DETAILS_ASSET_PACKAGE_1_idx | 111 | dcf_loan.ap.asset_package_id | 1 | Using where || 2 | DERIVED | ra | ref | FK_RETURN_APPLICATION_DOCUMENT_1_idx | FK_RETURN_APPLICATION_DOCUMENT_1_idx | 111 | dcf_loan.ld.loan_document_id | 1 | Using where |+----+-------------+------------+------+-----------------------------------------------------------+-----------------------------------------+---------+------------------------------+------+----------------------------------------------+只需运行0.01秒
0 0
- MySQL SQL 优化案例:JOIN派生表
- SQL优化:子查询->派生表->join关联
- mysql sql force_index 优化案例
- MySQL中SQL优化案例
- mysql无法优化的sql案例
- MySQL SQL优化案例:相关子查询(dependent subquery)优化
- MySQL优化案例---半连接(semi join)优化方式 导致的查询性能低下
- hive sql join优化
- SQL JOIN 优化
- mysql的join优化
- MySQL join 查询优化
- MySQL优化之JOIN
- mysql-join优化
- MySQL left join优化
- MySQL5.7性能优化系列(二)——SQL语句优化(2)——使用 Semi-Join半连接变换优化子查询,派生表和视图
- EXPLAIN sql优化方法3 DERIVED 派生表
- MySQL 对一段时间内每天数据统计案例--sql优化
- MySQL 对一段时间内每天数据统计案例--sql优化
- Nodejs源码分析之Console
- Java实现对MongoDB的AND、OR和IN操作
- Photos(PHObjectChangeDetails)
- redis主从同步配置和原理
- iOS画虚线
- MySQL SQL 优化案例:JOIN派生表
- github常用技巧记录
- Android安全-对称加密和非对称加密
- Redis主从配置和切换
- angularjs开发常见问题-3(angularjs 解决keydown keypress 不好用现象)
- mysql 常用操作
- Android Init进程源码分析
- hdu 1588 矩阵
- CFX WebService做的一个简单的HelloWorld例子 也可与spring 整合 发布在容器里面