SQL优化实战:让查询沿着索引扫描以提升性能
创作时间:
作者:
@小白创作中心
SQL优化实战:让查询沿着索引扫描以提升性能
引用
CSDN
1.
https://blog.csdn.net/weixin_40345397/article/details/140650885
在处理大量数据集排序并取前N条记录的场景中,SQL优化是一个常见的挑战。本文将通过具体的SQL语句和执行计划对比,深入探讨如何让查询沿着索引扫描,以显著提升性能。
问题背景
在数据库查询中,经常需要对大量数据集进行排序,然后从排序后的集合中取前部分结果。按照常规思路,系统会先读取所有符合条件的数据,然后进行排序,最后取出极少量结果。这个过程中,大量数据的扫描读取、过滤、排序会消耗掉大量的系统资源,导致SQL性能问题。实践中,几分钟乃至几个小时不出结果的情况很常见。
为了优化这种场景的SQL,我们经常会让查询顺序扫描建在排序列上的索引,以避开大量的数据读取和排序。但是,当索引列不在条件中出现时,Oracle数据库不会产生扫描索引的计划,即使使用hint也不能让查询沿着目的索引扫描。
问题重现
我们创建一个简单的表t1并为其添加索引:
create table t1(c1 int,c2 char(10));
create index idx1_t1 on t1(c1);
然后尝试以下SQL查询:
select * from (
select * from t1 order by c1
) where rownum<6;
这个查询的执行计划如下:
从计划中可以看出,系统会先读取表,再进行排序,然后取前5条记录。
尝试优化
如果我们尝试使用hint来强制让查询沿着索引扫描:
select /*+ index(t1,idx1_t1)*/* from t1 where rownum<6;
但是,执行计划显示并没有按照hint的指示执行:
这说明Oracle优化器认为在这种情况下走索引比全表扫描效率更低,因此即使使用hint也会被忽略。
解决方案
为了解决这个问题,我们可以在where条件中添加一个对索引列的条件,即使这个条件看起来是多余的:
select /*+ index(t1,idx1_t1)*/* from t1 where rownum<6 and c1<>-1;
修改后的执行计划如下:
从计划中可以看出,这次查询确实按照索引扫描的方式执行了。
总结
通过这个案例,我们可以总结出优化类似场景的两个关键点:
- 排序列上存在索引;
- where条件中有该索引列上的条件;
如果能实现按照索引扫描,性能提升可能达到成千上万倍,这一点在实践中得到了验证。
热门推荐
太湖鼋头渚:无锡千年的自然与历史交融
无锡四大热门景点全攻略:鼋头渚、拈花湾、惠山古镇、灵山胜境,哪个最值得去?
《红楼梦之金玉良缘》里的这些细节信息量太大,越品越上头!
拉布拉多的英文名,你知道多少?
狗狗英语表达大集合:从基础词汇到趣味俚语
王叔快点可以吗我赶去上班:如何高效解决通勤中的焦虑与时间浪费
自驾游免责条款怎么写
《流浪地球2》3D版和纪录片《流浪地球2:再次冒险》定档
展览|本南的新年礼物又如约而至,请打开这份“新春娱乐指南”
广东面积最小的城市,山海风光美不胜收,大家都去这条路打卡
光头强失忆了?网友热议背后真相揭秘
原神凯亚实战评测:冰属性主C养成攻略
凯亚生日揭秘:多重身份背后的真相
《原神》凯亚角色造型火遍全网,艺术设计揭秘
曾国藩“八本”论助力现代廉政建设
曾国藩的廉洁思想:清朝官场的清流
《战争之王》台词揭秘:幽默与讽刺中的深刻思考
揭秘《熊出没》配音演员:从幕后到台前的辛酸与荣耀
珍珠丸子:冬日家庭聚餐必备
连城珍珠丸子:一颗“非遗明珠”的传承与创新
樊荣辉教你做珍珠丸子,健康又美味
亲子DIY:珍珠丸子的快乐时光
小型鱼饲养秘籍:选对饲料很重要!
丰年虾:小鱼苗的最佳美食选择
曾国藩的廉洁自律:现代职场人的必修课
没有备份如何恢复微信聊天记录及预防丢失方法
開刀後飲食這樣吃,康復更快更有效:營養師專業建議
骨科手术伤口护理指南
名著导读:《红楼梦》选读
海北到四川九寨沟旅游小吃攻略:沿途美食与景点推荐