将主键从 varchar 更改为 int

use*_*288 3 mysql database-design primary-key

我有一张user表,用varchar作主键。现在从另一个地方我得到了intvarchar主键更好的性能提示。

所以我想将我的主键更改为int. 为此,我创建了另一个user表并将数据复制到该表中,但先前的主键值除外。

到此为止没有问题。

现在我的问题是我有很多表,它们user通过以前的主键与表相关。现在我想将其他表的行与新的主键值相关联。

这该怎么做?

小智 7

如果要更改主键,则不必制作另一个表。

我将执行的步骤是:

  1. 添加将成为主键的新整数列。
  2. 唯一值填充它,并确保对它有唯一约束。(它必须是唯一的才能确定它可以成为主键)
  3. 在每个子表中为外键添加一个整数列。
  4. 通过查找旧外键填充新外键。

例如

表用户(
 oldID varchar(10),
 newID int, -- 添加的新列,我假设此时您已填充该列
 ...
)

tbl用户登录(
 keyUser_oldID varchar(10),
 keyNewID int NULL,
 ...
)

运行以下...这些天我主要使用 SQL Server,所以希望这个伪代码给出了正确的想法。该原则适用于任何主要的基于表的数据库系统。

更新 tblUserLogin
SET keyNewID = (SELECT newID FROM tblUser WHERE oldID = keyUser_oldID
  1. 在两个列之间添加外键。
  2. 确保新的主键设置为自动递增。
  3. 一旦 oldID 和 keyUser_oldID 在您可以删除这些列的任何地方不再被引用。但只有在你完全确定之后!

需要考虑的几件事

这是一般原则,需要考虑一些事项。

  • 这适用于简单的情况,并假设您可以让人们暂时停止使用数据库,并且任何使用这些表的代码都已准备好切换为使用新的列名。
  • 子查询不是最有效的方法,但这是一项一次性任务,除非您有数百万行并且进行切换的时间有限,否则应该没问题。
  • 你没有说你在 varchar 字段中存储了什么?如果它是一个数字(但采用 varchar 格式),您可以随时执行 UPDATE tblSomeTable SET keyNewID = CAST(keyOldID as int) 这会更快更容易。

不过最重要的是...

..你没有提到数据库是否用于任何重要的事情。即使不是:

  • 如果您还没有,请事先备份。如果您在更新语句中出错,您始终可以引用备份副本。
  • 仔细思考这些步骤,这些都是结构性变化,花 30 分钟进行计划可以在以后节省数小时的时间。
  • 有一个备用计划,以防出现问题!