【高级开发必掌握SQL】SQL优化篇

article/2025/9/19 3:11:42

❤️作者主页:小虚竹

❤️作者简介:大家好,我是小虚竹。Java领域优质创作者🏆,CSDN博客专家🏆,华为云享专家🏆,掘金年度人气作者🏆,阿里云专家博主🏆

❤️技术活,该赏

❤️点赞 👍 收藏 ⭐再看,养成习惯

PC端左侧加我微信,进社群,有送书等更多活动!

前言

虚竹哥最近在写数据库方面的技术专栏,想输出好的技术知识时,也需要不断地输入,给人一瓢水,底下是一桶水。
今天来聊一聊SQL的性能优化,然后分享一个关于SQL的开源项目。
在分享之前,来个福利预告:认真看完文章,文末送本数据库好书。

SQL

SQL作为目前最常用的数据处理语言,广泛应用于查询、跑批等场景。当数据量较大时,使用SQL(以及存储过程)经常会发生跑得很慢的情况,这就要去优化SQL。优化SQL有一些特定的套路,通常先要查看执行计划来定位SQL慢的原因,然后针对性改写来优化SQL,比如对于连续数值判断可以用between来替代in,select语句指明字段名称,用union all替代union,把exists改写成join等。当然还有一些工程上的优化手段,如建立索引,使用临时表/汇总表等,优化的方法有很多,相信各位DBA都不会陌生。

但遗憾的是,仍然有相当多情况无论怎样优化都不可能跑得更快。这里做 SQL 性能优化真是让人干瞪眼 介绍了一些,并做了相应的技术分析。由于其理论基础关系代数的局限,SQL缺乏离散性和有序集合等特性的支持使得SQL在表达某些高性能算法时异常困难,甚至完全写不出来,只能采用比较笨的低性能算法,眼睁睁地看着硬件资源被白白浪费。在 写着简单跑得又快的数据库语言 SPL 中有对SQL理论基础缺陷的通俗解释。也就是说,SQL的慢是理论性的,这种问题仅仅由数据库在工程层面优化只能局部改善(确实有不少商业数据库能够自动识别某些SQL并转换成高性能算法),而不能根本地解决问题(情况复杂时数据库优化引擎都会“晕”掉,只能按SQL的书写逻辑执行成低性能算法)。理论性的缺陷当然也不能寄希望于更换数据库而得到解决,只要还是用SQL,即使采用分布式数据库、内存数据库也还是这种情况,在消耗更大成本的资源后当然也能有一定的性能提升,但和硬件本应能够达到的性能仍然有巨大的差距。

那还能怎么办?

那就不能再用SQL!也就不能再用关系数据库了。

那用什么?

SQL描述不了这些高性能算法,用Java,C++行吗?

没问题!从理论上讲,Java、C++什么算法都能实现,而且因为可以控制计算机底层的动作,这类代码通常可以跑出很好的速度(只要程序员能力不是太差)。

不过,不要高兴得太早,虽然都写得出来,但由于这些开发语言过于原生,本身没有提供什么面向数据处理的高性能计算类库,想实现这些算法就必须从头实现,而这恐怕要累死。以哈希关联为例,Java实现至少要写几百行代码,不仅要设计合适的哈希函数,还要解决可能出现的哈希冲突,这一套下来的工程量可不小;还有在Java中进行多线程编程也并非易事,但并行计算又是提升计算性能的有效手段。类似的,涉及结构化数据计算的算法还有很多,这些都自己来做的复杂度可想而知。如果一个计算的实现过于复杂,其开发代价已经远远超过性能优化本身,那也就没有优化的意义了。

Python也面临类似的问题,虽然在结构化数据计算类库方面要比Java丰富得多,但并没有提供必要的高性能算法库和存储方案,比如没有提供为大数据服务的游标类型及相关运算,也没提供有效的并行机制。想要实施那些高性能算法也只能自己开发,但Python作为解释执行语言,本身运行效率不高,在此基础上再开发的算法也往往达不到高性能要求。同样,Scala也缺乏足够的高性能计算类库,自己编写的算法同样复杂度相当高,对于不熟悉这些算法的程序员来讲,从头实现的代码的运行效率往往还不如努力优化后商用数据库SQL的速度。

那就只能忍受SQL的慢了吗?

还可以用SPL!

SPL和高性能

开源SPL(Structured Process Language),一个专门面向结构化数据处理的程序语言。使用SPL可以让原本SQL跑得慢的计算变快。

为什么SPL能跑得快?是拥有了什么改变硬件性能的黑科技吗?

那倒没有。软件改变不了硬件的计算性能,SPL也一样。简单来说,SPL快就是上面说的,要使用更高性能的算法。SPL中提供了大量基础的高性能算法类库,基于这些算法库实现的代码可以有效减少计算量,而我们做计算就是组合运用这些算法,每种计算都快一些,那整体上就会快很多,从而达到提升计算性能的目的。

SPL设计的这些高性能算法,像遍历复用、有序归并、外键预关联、标签位维度、并行计算等,都已经封装好。这其中有很多算法都是SPL独创的,在业内也是首次出现。

基于这些封装好的算法库,再写程序会就很方便,拿来直接用而不需要从头自己开发,不仅性能高,开发也快。从这个角度来看,跑得快和写着简单其实是一回事,就是能高效率地编写高性能算法。反观Java、C++、Python、Scala由于缺少这些算法库,想要实现高性能也就很难了。

这里有一些SPL 中高性能算法的例子及与SQL的对比用例:
性能优化技巧:遍历复用
性能优化技巧:TopN
性能优化技巧:预关联
性能优化技巧:外键序号化
性能优化技巧:附表
性能优化技巧:单边分堆
性能优化技巧:有序分组

SPL采用和SQL不同的观念看待同一个计算任务,继而可以采用不同(更低)复杂度的计算方法。

在实战中,SPL目前已经做过不少性能优化案例,少则提速数倍,多则数十倍,极端情况还有提速上千倍的,提速一个数量级基本上是常态。

比如在优化某保险公司车险保单跑批的案例( 开源 SPL 优化保险公司跑批优从 2 小时到 17 分钟 )中,使用SPL将计算时间从2小时缩短到17分钟,同时代码量减少了2/3。这里使用了SPL特有的遍历复用技术,可以在对大数据的一次遍历过程中实现多种运算,有效地减少外存访问量。这个案例涉及对一个大表进行三次关联和汇总的运算,使用SQL要将大表遍历三次,而使用SPL只需要遍历一次,并在关联运算上也采用了不同的方法,因此获得了巨大的性能提升。

还有在 开源 SPL 将银行手机账户查询的预先关联变成实时关联 的案例中,使用SPL将原本只能预关联的手机账户查询变成实时关联,同时服务器数量从6台降为1台。这里充分利用了SPL的有序存储机制,一次性读取整个账户数据时可以有效减少硬盘时间(物理存储连续),再借助区分维表和事实表的外键实时关联技术使用单机就能完成实时关联查询,性能提升明显,硬件需求也降低了许多。

这里还整理了一些常见的业务场景,可以利用SPL的算法库来实现的高性能:

如何让 JOIN 跑得更快?

内存数据库如何发挥内存优势?

列存数据仓库怎样更高效

高并发帐户查询怎么做?

多标签用户画像分析跑得快的关键在哪里?

双维有序结构提速大数据量用户行为分析

关于SPL高性能的原因在 快出数量级的性能是怎样炼成的 里也进行了详细分析,并给出了更多实际优化案例供参考。

进一步讨论

说到这里你可能会想,那是不是学会SPL语法就能把计算跑得快了?

也没这么简单!

关于算法

使用SPL可以获得更高性能不是因为SPL语法,SPL语法虽然有些特色,但并不是跑得快的根本原因。最关键的是掌握和运用高性能算法

实现性能优化有两步:第一步设计出低复杂的计算方案,第二步用足够低的成本实现它。其中更关键的是第一步,这需要由有一定经验和知识储备的程序员来做(即掌握和运用高性能算法),第二步才是用SPL来做。换句话说,SPL并不负责设计解决问题的方法,而只是负责让解法更容易实现出来。

SPL语法很简单,比 Java 容易得多,两小时就能基本上手,两三周就能比较熟练了。但算法却没那么简单,需要认真学习反复练习才能掌握。反过来,只要掌握了算法,用什么语法就是个相对次要的问题了(当然用 SQL 这种太粗线条的语言还是不行)。这就像给病人看病,找出病理原因后,能分析出什么成分的药能管用。无论直接购买成药(使用封装过的 SPL),还是上山采药(使用 Java/C++ 硬写),都可以治好病,无非就是麻烦程度和支付成本不同。

因为实际中很少使用,有不少应用程序员工作几年后都把大学时代学过的数据结构和算法课程内容忘了,而不理解这些基础算法知识时也就没办法设计出高性能算法方案。为此,SPL设置了专门的高性能专题,不仅涵盖高性能算法与优化技巧,还有性能优化课程与性能图书来授人以渔。

高性能计算专题

性能优化图书

性能优化课程

关于存储

和算法密切相关的,高性能计算还有一个关键点是数据存储,高性能计算离不开合理的数据存储方式。使用SPL实施高性能计算时也不能再基于数据库来做,需要将数据从数据库里搬出来重新组织。

为什么呢?

慢的数据计算任务可以分为计算密集型和数据密集型两大类。单纯的计算密集型任务涉及的数据量不大而只是计算量很大,计算量大并不是由于数据量大造成的,这样不用改变存储方式,只要实施了好的计算方法也能大幅提升性能,也就是说,可以继续在原有的存储方式(比如数据库)上使用SPL来优化性能。而数据密集型任务涉及的计算量也很大,但计算量大主要是由数据量大造成的,这时候如果不改变存储方式,数据读取时间很可能会很长,即使能把计算时间优化到0,整体运算时间也不能得到有效的优化。

遗憾的是,我们面临的计算慢的场景绝大部分属于数据密集型计算。如果数据还存在数据库中,而数据库取数接口(如JDBC)通常又非常慢,将数据读出就要消耗很长时间(IO效率很低),经常远远超过后续SPL计算的时间,这也就不可能达到优化效果了。而且,SPL中有相当多的算法也对存储组织有要求,比如单边分堆算法就要求有序的存储方式,而常规关系数据库无法满足这个前提,这些算法也无法实施了。

为了解决这个问题,SPL提供了自有的存储机制,直接采用文件系统,将数据从数据库导出到特定格式的文件中,不仅可以获得更高的IO存取效率以及文件系统灵活的管理能力,还可以充分利用自有格式的列存、有序、压缩、并行分段等数据存储优势,从而高效地发挥高性能算法效力。

使用文件存储数据还可以有效减少数据入库的时间,进一步提升计算性能。有些计算场景不仅要从数据源读,还要将计算结果落地,存入数据库以方便后续计算使用。像ETL就是典型的读写并存的计算,还有某些大数据计算或复杂计算需要将中间结果暂存,后续计算还需要再使用的情况。我们知道,数据库写入是非常慢的动作,伴随写入的计算场景性能自然低下。这时就可以将原本需要入库的数据存储在文件中(虽然这是工程方面的优势,但仍可获得接近数量级的读写性能提升),再利用SPL的文件计算能力直接计算,从而实现高性能。

关于T+0

如果把数据都移到数据库外,那么是不是就无法完成实时数据计算了?毕竟数据总是在不断地产生。

没有问题。

对于全量T+0实时查询,SPL提供了多源混合计算的能力以满足这类场景。冷数据量大且不再变化使用SPL的高性能文件存储,这样可以获得更高地计算性能;热数据量小仍然存放在原有数据源中,SPL直接读取计算(支持多样性数据源),由于热数据量并不大,直接基于生产数据源查询也不会对其造成太大影响,访问时间也不会太长。冷热数据混合计算,就可以获得针对全量数据的T+0实时查询。我们只要定期将变冷的数据固化到SPL的高性能存储中,原数据源只需要保持少量近期新产生的热数据即可。整体架构如下:

如何开始

从前面的分析可以知道,完成性能优化任务必须熟悉高性能算法和存储机制,但从上面的课程图书也可以看出来,这些内容并不少,都要融会贯通也不是很容易的事。特别是很多程序员都习惯了SQL的思维方式,很难跳出这个窠臼。面对一个性能优化任务,即使有了开源SPL这样的有利武器,也常常有点无从下手。打个比方,一个赶马车的高手想跑得更快时,会习惯于寻找缰绳和鞭子,而对于初次见到的汽车上的方向盘和油门却会感到一头雾水。

为此,SPL团队也提供相应的咨询服务:你可以把遇到的性能问题拿过来与我们一起讨论和设计优化方案,必要的时候还可以进行POC。

我们通常关心这样一些必要的问题信息:业务场景、面临痛点、当前计算的数据量和并发量以及响应时间,如果还能提供SQL脚本、表结构和测试数据就更好了。留个邮箱方便交流:spl@scudata.com。

相信我们,从不失手!

经历过一两个案子,程序员们就会熟悉SPL的思维方式(理解了方向盘和油门),以后再自己做性能优化就不是问题了。

天下武功,唯快不破,但只有掌握了快的本质和方法才能所向无敌。你说是不是?

相关资料

  • SPL下载
  • SPL源代码

粉丝福利

送一本这个月刚出版的《MySQL数据库进阶实战》《MySQL数据库进阶实战》读后感
如何免费获得该书呢?

  • 参与评论送书:随机抽取一位幸运读者,送一本《MySQL数据库进阶实战》!
  • 统计截止时间:2022/08/18 21:59:59

http://chatgpt.dhexx.cn/article/r8sA1NlP.shtml

相关文章

SQL优化方案

转载至:http://blog.itpub.net/31555484/viewspace-2565387/ 作者1:惨绿少年 https://www.cnblogs.com/clsn/p/8214048.html 作者2:喜欢拿铁的人 https://zhuanlan.zhihu.com/p/49888088 在进行MySQL的优化之前,必须要了解的就是MySQL的查询过程&am…

慢SQL优化

1、慢查询统计 show VARIABLES like %que% SET GLOBAL slow_query_log on; //开启慢sql统计开关 SET GLOBAL long_query_time 1; //设置超过1秒则 认为是慢sql , 注意此处设置完之后需要重新链接客户端 才可以查看到设置成功 2、优化 索引优化 通过执行计划&…

Oracle数据库SQL优化详解

Oracle数据库SQL优化 1. Oracle SQL优化概述2. Oracle SQL优化详解2.1 Oracle 查询阻塞2.2 Oracle 查询耗时 SQL2.3.Oracle 查看执行计划2.4.Oracle 查看收集统计信息2.5.Oracle 查询优化器 -- 改写查询语句2.6.Oracle 查询优化器 -- 访问路径2.7.Oracle 查询优化器 -- 表连接方…

Mysql sql优化

这里引用深入Mysql实战 为什么要优化 提高资源利用率避免短板效应提高系统吞吐量同时满足更多用户的在线需求 简单来说,优化的目的是为了提高资源的利用率,让资源充分发挥价值。常见场景下,一台服务器有四大资源:cup、内存网络…

sql优化的15个小技巧

最近找了找怎么优化SQL,总结了15个基础技巧 因为最近一直在写sql的原因,所以需要知道sql该怎么优化,怕哪一天线上的接口,出了问题,需要优化,就需要采用改造成本最小的. 先上个导图 1.避免使用 select * 很多时候,我们写sql语句时,直接使用select *&am…

聊聊sql优化的15个小技巧

前言 sql优化是一个大家都比较关注的热门话题,无论你在面试,还是工作中,都很有可能会遇到。 如果某天你负责的某个线上接口,出现了性能问题,需要做优化。那么你首先想到的很有可能是优化sql语句,因为它的…

SQL优化的方法

(1)建立物化视图或尽可能减少多表查询。 (2)以不相干子查询替代相干子查询。 (3)只检索需要的列。 (4)用带in的条件子句等价替换or子句。 (5)经常提交com…

sql优化的N种方法_持续更新

当你访问网站的时候,有的时候会慢的想让你砸电脑,这个时候服务器要背锅了吗? 不,要背锅的不仅仅是服务器,数据库也有很大责任,不负责任的sql开发者更会让你崩溃的.为了提高sql响应速度,还是好好了解下sql的优化吧 sql优化的方式 一:sql性能分析 sql优化首先要对sql的消耗时…

sql优化常用的几种方法:19种最有效的sql优化技巧

我们来谈谈项目中常用的MySQL优化方法,共19条,具体如下: 1、EXPLAIN 做MySQL优化,我们要善用EXPLAIN查看SQL执行计划。 下面来个简单的示例,标注(1、2、3、4、5)我们要重点关注的数据&#x…

sql优化的15个小技巧(必知五颗星),面试说出七八个就有了

目录 前言 1 避免使用select * 2 用union all代替union 3 小表驱动大表 4 批量操作 5 多用limit 6 in中值太多 7 增量查询 8 高效的分页 9 用连接查询代替子查询 10 join的表不宜过多 11 join时要注意 12 控制索引的数量 13 选择合理的字段类型 14 提升group by的…

MySQL高级篇(SQL优化、索引优化、锁机制、主从复制)

目录 0 存储引擎介绍1 SQL性能分析2 常见通用的JOIN查询SQL执行加载顺序七种JOIN写法 3 索引介绍3.1 索引是什么3.2 索引优劣势3.3 索引分类和建索引命令语句3.4 索引结构与检索原理3.5 哪些情况适合建索引3.6 哪些情况不适合建索引 4 性能分析4.1 性能分析前提知识4.2 Explain…

Sql优化总结!详细!(2021最新面试必问)

Sql优化 Sql执行顺序基础Sql优化查询SQL尽量不要使用select *,而是具体字段避免在where子句中使用or来连接条件使用varchar代替char尽量使用数值替代字符串类型查询尽量避免返回大量数据使用explain分析你SQL执行计划是否使用了索引及其扫描类型创建name字段的索引优…

如何破解VS2015(使用秘钥)

【时间】2018.10.07 【题目】如何破解VS2015(使用秘钥) 安装完vs2015 企业版/专业版后,在菜单帮助---注册产品,会显示产品试用期30天,怎么破解呢?其实只要输入相应的秘钥即可完成破解。如若不破解&#x…

vs2015激活码

microsoft visual studio2015是微软推出的一款集程序设计网页开发于一身的开发工具。microsoft visual studio 2015支持c,c,c#以及手机应用开发,用它所写的目标代码适用于微软支持的所有平台,包括Microsoft Windows、Windows Mobile、Windows CE、.NET F…

VS2017 激活密钥

【时间】2018.11.26 【题目】VS2017 激活密钥 一、激活秘钥 Enterprise[企业版]: NJVYC-BMHX2-G77MM-4XJMR-6Q8QF Professional[专业版]: KBJFW-NXHK6-W4WJM-CRMQB-G3CDH 二、秘钥使用 使用位置在 帮助 -- 注册商品 中: 输入秘钥后,激活成功后&a…

Android APP性能测试以及性能指标

Android的app性能测试包括的测试项:Activity响应时间,帧率,内存,cpu消耗,耗电量,冷启动 Activity响应时间的相关测试 查看当前APP打开的页面命令: adb shell dumpsys activity | findstr mResumedActivity然后用命令去打开APP的某个activ…

APP性能测试之GT 测试

APP性能测试之GT 测试 1 什么是 GT GT(随身调)是腾讯研发的开源 APP 随身调测平台,它是直接运行在手机上的“集 成调测环境”(IDTE, Integrated Debug Environment)。 GT 仅凭一部手机,无需连接电脑&a…

面试百问:如何测试App性能?

APP性能测试几乎是客户端面试必问。 为什么要做App性能测试 如果APP总是出现卡顿或网络延迟的情况,降低了用户的好感,用户可能会抛弃该App,换同类型的其他应用。如果APP的性能较好,用户体验高,使用起来丝滑顺畅&…

APP性能测试之IOS性能测试-instruments使用

最近在做APP的性能测试,已经在运行阶段,所以来总结下,本文章主要是讲的是IOS性能测试,我这边做的是内存漏洞分析和app启动时间/CPU占用/Core Animation等等,基本都试过了,说一下搭建过程吧 1.准备一个MAC电…

如何进行App性能测试?SoloPi是最佳选择!

目录 引言 SoloPi简介 SoloPi特点 SoloPi的主要功能 下载SoloPi 安装SoloPi 使用SoloPi进行性能测试 性能数据查看与记录 环境加压 响应耗时计算工具 注意事项 Solopi提供的各项性能指标介绍 引言 大家好!我是凡哥。 今天我想跟你们分享一下如何进行A…