前言
毫不夸张地说,无论我们的后端工程师在哪家公司,呆在哪个团队,做哪个系统,第一个头疼的问题绝对是数据库的性能。如果我们有一套成熟的方法论,我相信我们可以快速准确地解决我们每天遇到的80%甚至90%的性能问题。
从解决问题的角度来看,我们必须首先了解问题的原因;其次,我们必须有一套思考和判断问题的过程,让我们合理地选择解决方案;最后,从许多解决方案中选择合适的解决方案,找到合适的解决方案的前提是我们对各种解决方案之间的优缺点和场景有足够的了解。没有一个解决方案是完全通用的,软件工程也没有银弹。
以下是我工作多年以来使用的八个计划。结合我通常学习和收集的一些信息,我以系统和全面的方式整理成这篇博客文章。我也希望一些有需要的同行能在工作和成长中提供一些帮助。
为什么数据库会慢?
无论是关系数据库还是 NoSQL,任何存储系统能的存储系统主要有三种:
- 时间复杂
- 数据总量
- 高负载
有两个主要因素决定了搜索时间的复杂性:
- 查找算法
- 存储数据结构
无论是哪种存储,数据量越少,自然查询性能越高。随着数据量的增加,资源的消耗(CPU、磁盘读写繁忙),耗时也会越来越高。
从关系数据库的角度来看,索引结构基本固定B Tree,时间复杂度是O(log n),存储结构是行式存储。因此,我们只能优化关系数据库的数据量。
高负荷的原因包括高并发请求、复杂查询等CPU、磁盘繁忙,服务器资源不足会导致慢查询等问题。
这类问题通常通过集群和数据冗余来分担压力。
应该站在哪个层面思考优化?
从上图可以看出,自上而下有硬件、存储系统、存储结构和具体实现四层。
层与层紧密相连,每层上层为层的载体;因此越往顶层越能决定性能的上限,同时优化的成本也相对会比较高,性价比也随之越低。
以底层的具体实现为例,索引优化的成本应该是最小的。可以说,添加索引后,无论是 CPU 消耗或响应时间立竿见影。
然而,一个简单的句子,无论如何优化和索引也是有限的,当没有任何优化空间的具体实现层存储结构,思考是否从物理表设计优化(如库表、压缩数据量等),如果是文档数据库必须考虑文档聚合的结果。
如果存储结构的优化没有效果,我们必须继续考虑上次。关系数据库是否不适合当前的业务场景?
如果要更换存储,如何更换 NoSQL?
因此,出于性价比的优先考虑,我们的优化理念是具体实现的。没有优化的空间。当然,如果公司有钱,直接使用钞票的能力,绕过前三层,这也是一种方便的应急处理方法。
本文不讨论顶部和底部的优化,主要从存储结构和存储系统中间两层的角度。
总结八大方案
数据库优化方案有三个核心本质:减少数据量,用空间换性能,选择合适的存储系统。
这也对应了开头慢解释的三个原因:数据总量、高负载、查找的时间复杂度。
以下是收入类型的一般解释:短期收入、低处理成本、紧急响应,长期存在技术债务;长期收入与短期收入相反,短期处理成本高,但效果可长期使用,可扩展性更好。
静态数据意味着相对变化频率较低,不需要过多的联表,where 过滤较少。相反,动态数据更新频率高,通过动态条件筛选过滤。
减少数据量
减少数据量