Sql 复合主键的重新排序组合

Sql 复合主键的重新排序组合,sql,sql-server,database-design,composite-primary-key,primary-key-design,Sql,Sql Server,Database Design,Composite Primary Key,Primary Key Design,我有一张桌子 documents ( year int not null, number int not null, document_types_id int not null, ... ) 主键是年份+编号+文档类型\u id 我认为更好的主键应该是年份+文档类型+id+编号。有没有一种方法可以在不删除和重新创建PK的情况下重新排列此组合(而不是表、PK和FK组合中的列),因为此PK在许多其他表中用作FK 谢谢。如果在其他表上删除FK是一个问题,那么您

我有一张桌子

documents
(
    year int not null, 
    number int not null, 
    document_types_id int not null, 
    ...
)
主键是年份+编号+文档类型\u id

我认为更好的主键应该是年份+文档类型+id+编号。有没有一种方法可以在不删除和重新创建PK的情况下重新排列此组合(而不是表、PK和FK组合中的列),因为此PK在许多其他表中用作FK


谢谢。

如果在其他表上删除FK是一个问题,那么您可以使用这些列的顺序创建一个非聚集索引,并提供提示(使用索引)(ALTER TABLE语法没有为
ALTER CONSTRAINT
语句留下作用域。

您必须先删除主键,然后再对其进行更改。否则您会收到一条消息,即一个表上不能有两个主键

但是那没问题,只要做就行了

Alter Table myTable NOCHECK Constraint All
然后随意改变你的桌子,然后

Alter Table myTable CHECK Constraint ALL
你很好

MySQL中的等价物是:

SET FOREIGN_KEY_CHECKS = 0;


外键引用主键,因此外键是三维的(年份+编号+文档类型\u id)。如果要删除维度,则即使尝试修改主键,约束也会告诉您无法删除给定列,因此您应该先处理外键,然后再修改主键。步骤:

  • 将所有外键写入一个列表,以使您能够知道哪些是以前的外键

  • 去掉所有引用主键的外键

  • 修改/重新创建主键

  • 根据主键的新版本重新创建外键


  • 不。在关系模型中,键中的属性没有有意义的排序。但在SQL中,有。外键的列与FK引用的主键或唯一键的列之间的对应关系是按顺序位置,而不是按名称

    因此,键声明中列的顺序是有意义的,如果当前有效地使用了该含义/顺序,那么在不中断当前使用的情况下,您无法对其进行更改


    此外,该理论对关键属性/列的排序没有任何意义,这并非没有道理。您认为“重新排序”的“更好”是什么密钥,与现有的密钥相比?

    这是一种预感,还是您测试过该主键的性能更好?我不打算更改生产数据库上的PK和FK。首先,我想测试这种组合的性能。您可能有一些脚本来测试它,而不仅仅是看看它将如何运行。或许可以尝试runn用现有的脚本编写一个解释计划,然后用一个新的列顺序设置一个唯一的索引。如果新的索引给出更好的性能,你会在计划中看到这个。只有那时我才会考虑触摸主键。即使这样,也可能是根据其他脚本可能使用它而将它放在适当的位置。这不适用于SQL Server,是真的吗?哦,糟糕,我认为这是关于MySQL的。更新了我的答案。步骤1a:锁定数据库和步骤5:解锁是的,你是对的,我对你的评论投了赞成票。在这四个步骤之间是我的四个步骤,但为了安全起见,锁定数据库是一个好主意。对我来说,使用类型更自然s_id+数字PK而不是数字+类型PK。这样更好吗?我不知道。我有一个想法:如果我们用重新排序的PK执行简单的select语句,我们将得到按年份、类型和编号排序的文档。然后,如果我们需要具有特定类型的文档,它们都是按顺序排列的(一个接一个)在结果集中。使用相同的select语句,如果PK是结果集中的year+number+types\u id,我们会得到按数字排序的记录,然后是按类型\u id。为了更好地理解我的想法:你认为错了。如果执行简单的select,你会得到随机排序。如果你在select中指定ORDER by,你只会得到可预测的排序。第二个想法:如果你您确实需要一些特定的排序,并且存在一些索引,这些索引的列排序顺序与您的order BY子句的顺序完全相同,那么系统可以在不重新排序/重新排列行的情况下满足您的请求。但是您仍然需要显式地指定所需的顺序。我如何获得随机排序?如果我们查看第二部分select-结果集按年份asc、类型\ id asc和编号asc排序(不含order by)。要清楚,我总是指定order by子句,这仅用于测试目的。我的想法是-如果我们在此pk(fk)上扩展查询和联接表,并将其添加到查询中:如果类型\u id=2 ORDER BY SEXT\u table\u带有\u documents\u FK.time\u updated DESC,则重新排序的PK(年份+类型\u id+编号)是否会给我们带来更好的性能,因为表文档上的select语句会给我们已经按类型\u id排序的列。
    SET FOREIGN_KEY_CHECKS = 1;