mysql - 主键自增

标签 mysql

我有一个包含两个表的数据库,当前每个表有 3 列。

Table_A:iduidurl

Table_B:iduidurl

id 是主键,在插入的每个新行上自动递增 1

我的问题是我还需要主键吗?我永远不会在数据库中查询iduid 列只是为了分隔每个用户,因此每行不是唯一的。 Table_ATable_B 将经常通过 uid 进行比较。 我有 uidurl 索引,我预计该表可能会增长数十亿,而且我不想在 id 上浪费空间.

最佳答案

如果您使用 InnoDB,并且没有声明主键列,InnoDB 将使用 6 字节整数为您创建一个主键列。因此,通过删除 id 列,您获得的唯一好处可能是用 8 字节 BIGINT 换取 6 字节隐式 PK 列。

原因是 InnoDB 表存储为 B 树,即基于主键的聚集索引。每个表都必须有一列用于组织此 B 树,即使它是隐式创建的列。

您还可以声明具有复合主键的表:

CREATE TABLE Table_A (
  uid INT NOT NULL,
  url VARCHAR(100) NOT NULL,
  PRIMARY KEY (uid, url)
);

在这种情况下,满足了主键的要求,并且 InnoDB 不创建隐式列。


回复您的评论:

我尽量不使用MyISAM。 MyISAM 比 InnoDB 更容易受到数据损坏的影响,并且通常 InnoDB 性能更好,因为它同时缓存数据和索引。确实,在某些情况下 MyISAM 可以使用更少的磁盘空间,但磁盘空间很便宜,我更愿意享受 InnoDB 的好处。

关于索引,如果您有PRIMARY KEY(uid, url),那么您将自动在这两列上拥有一个复合索引。无需在 uid 上创建额外的索引。

但是,如果您的查询仅搜索 url,而不查找特定的 uid,那么您需要在 url 上建立单独的索引。

我在演讲中详细讨论了索引设计:How to Design Indexes, Really

关于mysql - 主键自增,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14464837/

相关文章:

mysql - 需要帮助将 json 文字插入 mysql 5.7

Mysql 全文语法错误 #1215

mysql - 如何导入具有 ~350 列的 SQL 表?

mysql - 如果选择部分匹配该行的列之一,则触发对该行的列的更新

php - Eloquent 地选择组的最后一行

Mysql group_concat 按计数拆分

mysql - 在键重复的地方存储键值并使用主键

java - EasyPHP 上的数据库服务器无法启动

mysql - 计算并选择同一查询中列的最大值

java - 通过 Java 使用 MySQL