【问题标题】:The differences between INT and UUID in MySQLMySQL中INT和UUID的区别
【发布时间】:2015-08-08 07:47:52
【问题描述】:

如果我将主键设置为INT类型(AUTO_INCREMENT)或者设置在UUID,这两者在数据库性能上有什么区别(SELECTINSERT 等),为什么?

【问题讨论】:

  • 如果您能详细说明您目前所知道的内容,那么人们将能够填补空白 - 以及您的问题希望将来对其他用户有用
  • a int 是一种数据类型,UUID 是返回唯一字符串的函数/方法/过程(不确定术语)。要求不同是很困难的,因为他们几乎没有没有共同点。我猜你要的是auto increment 而不是......
  • 对不起,我没有把这个问题描述清楚。我的意思是如果我将主id键设置为int类型(自动增量)或UUID,数据库性能有什么区别(选择,insert...) 以及为什么
  • 在最新的评论更新后,我更新了我的答案,我认为它回答了你所有的问题

标签: mysql performance primary-key


【解决方案1】:

UUID 返回一个universal unique identifier(如果导入另一个数据库,希望也是唯一的)。

引用 MySQL 文档(强调我的):

UUID 被设计为一个在空间上全球唯一的数字,并且 时间。对 UUID() 的两次调用预计会生成两个不同的 值,即使这些调用是在两台不同的计算机上执行的 彼此不相连。

另一方面,一个简单的INT 主 ID 键(例如 AUTO_INCREMENT)将为特定的 DB 和 DB 表返回一个 唯一整数,但它是 不是普遍唯一的(所以如果导入到另一个数据库,可能会出现主键冲突)。

在性能方面,使用auto-incrementUUID 应该没有任何明显差异。大多数帖子(包括本网站作者的一些帖子)都是这样声明的。当然UUID 可能需要更多时间(和空间),但这对于大多数(如果不是全部)情况来说并不是性能瓶颈。将列作为Primary Key 应该使这两个选择与性能相同。请参阅以下参考资料:

  1. To UUID or not to UUID?
  2. Myths, GUID vs Autoincrement
  3. Performance: UUID vs auto-increment in cakephp-mysql
  4. UUID performance in MySQL?
  5. Primary Keys: IDs versus GUIDs (coding horror)

UUID vs auto-increment 性能结果,改编自Myths, GUID vs Autoincrement

UUID优点/缺点(改编自Primary Keys: IDs versus GUIDs

GUID专业人士

  • 在每个表、每个数据库、每个服务器中都是唯一的
  • 允许轻松合并来自不同数据库的记录
  • 允许在多个服务器之间轻松分发数据库
  • 您可以在任何地方生成IDs,而不必往返数据库
  • 大多数复制方案都需要GUID

GUID 缺点

  • 比传统的 4 字节索引值大 4 倍之多;这可能会产生严重的性能和存储影响,如果 你不小心
  • 调试麻烦 (where userid='{BAE7DF4-DDF-3RG-5TY3E3RF456AS10}')
  • 生成的GUIDs 应该是部分顺序的,以获得最佳性能(例如,SQL 2005 上的newsequentialid())并启用 聚集索引。

注意

我会仔细阅读提到的参考资料,并根据我的用例决定是否使用UUID。也就是说,在许多情况下,UUIDs 确实更可取。例如,可以在根本不使用/访问数据库的情况下生成UUIDs,或者甚至使用已经预先计算和/或存储在其他地方的UUIDs。此外,您可以轻松概括/更新您的数据库架构和/或集群方案,而不必担心 IDs 会中断并导致冲突。

就可能的冲突而言,例如使用 v4 UUIDS(随机),the probability to find a duplicate within 103 trillion version-4 UUIDs is one in a billion.

【讨论】:

  • 缺点:如果缓存对于整个 UUID 索引来说不够大,性能会很糟糕。
  • @RickJames,真实,并在引用的参考文献中提到
  • 这是一篇关于性能分析的好文章:percona.com/blog/2019/11/22/… 人们应该在实施 UUID 之前考虑其用例是否需要 UUID。在很多情况下,UUID 密钥可能非常有用。如果不是,它可能不值得。此外,应该说明的是,如果需要,UUID 列总是可以在以后添加到表中。
  • @JacobThomason,好文章。不过已经提到了 UUID 的存储要求,
【解决方案2】:

除非在数据库中持久化,否则 UUID 密钥不能为 pk,因此在此之前将发生往返,如果没有成功的事务,您不能假设它的 pk。大多数 UUID 使用基于时间、基于 mac、基于名称或一些随机 uuid。鉴于我们正在大力转向基于容器的部署,并且它们具有启动序列 MAC 地址的模式,依赖于 mac 地址将不起作用。基于时间并不能保证,因为假设系统始终处于精确的时间同步状态,这有时是不正确的,因为时钟不会遵循规则。 GUID 不能保证冲突永远不会发生,只是在给定的短时间内它不会发生,但如果有足够的时间和并行运行的系统以及保证最终会失败的系统的扩散。

http://www.ietf.org/rfc/rfc4122.txt

【讨论】:

    【解决方案3】:

    对于使用集群主键的 MySQL,版本 4 随机生成的 UUID 如果用作主键会影响插入性能。这是因为它需要对行重新排序以将新插入的行放置在聚集索引内的正确位置。

    FWIW,PostgreSQL 使用堆而不是集群主键,因此使用 UUID 作为主键不会影响 PostgreSQL 的插入性能。

    更多信息,本文对UUID和Int进行了更全面的比较:Choose Primary Key - UUID or Auto Increment Integer

    【讨论】:

      猜你喜欢
      • 2013-01-30
      • 1970-01-01
      • 2010-10-15
      • 2010-12-08
      • 1970-01-01
      • 2011-08-20
      • 1970-01-01
      • 2018-03-20
      • 2016-09-28
      相关资源
      最近更新 更多