多年前,我曾在一家远程信息处理公司工作,该公司从全球数十万台设备中收集数据。在公司实现了爆炸性增长的某个节点,我们迎来了一个新客户,这位客户为我们带来了大量新的设备,这直接推动了公司收入的大幅增长。这是公司发展过程中的一个伟大时刻,但随之而来的数据处理量增长却暴露了我们系统的一个巨大缺陷。数据历史表(记录所有设备发生的每个事件)的 ID 列被定义为 INT 数据类型,而它的存储空间很快就不足了。这个问题并没有马上成为现实,但如果该列空间耗尽,我们的整个系统将会停摆。有趣的是,我们还开发了一个名为“末日时钟”的简单工具,用来估算这个问题可能发生的日期。如果我们事先能预料到这一点,就会设计一个更好支持增长的数据库结构。但当然,很多决策的后果往往只有在事后才能显而易见。接下来,让我们深入了解这个问题,以及在设计数据库时可能出现的其他几个常见错误。


  1. 子优化的数据类型

本文开头介绍的场景凸显了在选择数据类型时需要考虑的问题:不仅要满足当前数据量的需求,还要能支持未来潜在的增长。这不仅适用于数值类型,还适用于字符串类型。例如,如果尝试在一个 VARCHAR(255) 的列中写入一个包含 300 个字符的字符串,而 MySQL 正处于严格模式(Strict Mode,默认为开启状态),那么 MySQL 会返回错误并拒绝写入。如果 MySQL 不在严格模式,超过长度的数据会被截断,从而导致可能重要的数据丢失。注意 如果你对 MySQL 中的各种字符串类型感兴趣,可以阅读我们关于字符串类型选择的文章,了解详细信息。与数据不足问题相反,列数据的存储空间过多也可能是问题所在。虽然不会像存储空间不足的情况那样严重,但过度预留空间会带来存储和性能方面的影响。比如,假设我们需要存储美国的 ZIP 邮政编码,这通常是五位数字。可以使用 INT 数据类型(存储 32 位整数)来处理邮政编码,但这样会分配的存储远远超过实际需求。使用 SMALLINT 会是更好的选择,因为它存储的是 16 位整数,足够处理邮政编码。这些只是设计列数据类型时可能面临的选择错误中的几个例子。


  1. 缺失或冗余的索引

索引在 MySQL 中通过构建一个经过优化的结构来加速数据访问,使查询更快地返回符合条件的数据。如果没有利用索引,当执行未分页或未定义 LIMIT 的查询时,MySQL 会对表执行扫描操作。扫描意味着它会从表的第一行开始逐行读取,直到找到匹配条件的所有行。如果某个被频繁访问的大表没有使用索引,从表扫描会带来巨大的性能损失。注意 如果你想了解缺失索引对性能的实际影响,我们的团队成员 Aaron Francis 曾成功帮助一个客户优化 SaaS 系统,并在 YouTube 上记录了整个过程!另一方面,索引过多也会带来问题。创建的每个索引都会占用额外的存储空间,因此冗余或未使用的索引会直接增加存储成本。此外,当表中的数据被更新或插入时,MySQL 会更新这些索引及其相关统计信息,以确保索引的准确性。这可能是一项耗时的操作,可能导致不良的用户体验。注意 如果你希望了解如何高效地使用索引,我们在 MySQL for Developers 课程中提供了完整的相关内容。


  1. 不当存储半结构化数据

过去 20 年间,越来越多的公司选择使用 NoSQL 来存储半结构化数据,以满足快速处理大量数据的需求。这类数据存储已经有很多专业解决方案,但实际上 MySQL 在这方面也很有能力。大多数存储在数据库中的半结构化数据通常是以 JSON 的形式表示。最简单的方式是将 JSON 字符串存储在 TEXT 类型的列中,但这并不是最佳选择。MySQL 支持一种专门用于存储 JSON 的列类型:JSON。这种类型会将 JSON 数据以高效的二进制格式存储。使用 JSON 而非 TEXT 类型有几个关键好处:

  1. 最为广泛使用的 MySQL 存储引擎 InnoDB 原生支持基于 JSON 对象内容的查询和过滤,这避免了在应用代码中手动过滤结果的需求。
  2. MySQL 还支持基于 JSON 数据创建索引,使得查询更加高效,可以加速基于 JSON 数据返回结果的操作。

注意 如果你希望进一步了解 MySQL 的 JSON 数据类型,我们的博客中有多个相关的文章,比如 JSON 类型基础如何为 JSON 列创建索引


结论

那么,那列空间不足的 ID 数据最终怎么解决了呢?幸运的是,这个列类型是有符号整数(signed integer),因此我们能够将 ID 重新设置为 -2,147,483,648,从而通过分配负数作为 ID 并递增至 0,有效地将 ID 容量翻了一倍。这并不是最优雅的解决方案,但这种方法确实帮助我们避免了因更新数据库模式而导致的大量停机时间(几乎所有表都需要进行变更)。为增长设计数据库绝非易事,问题也可能迅速变得复杂。本文仅介绍了几个潜在的数据库设计错误,但每个 MySQL 应用场景都是独特的,并具有自己的挑战。



三种常见的 MySQL 数据库设计错误插图

关注公众号:程序新视界,一个让你软实力、硬技术同步提升的平台

除非注明,否则均为程序新视界原创文章,转载必须以链接形式标明本文链接

本文链接:https://www.choupangxia.com/2025/09/14/three-common-mysql-database-mistakes/