想象您有一个创建了三个表的N-N关系。例如,您有一个用于CUSTOMER(id_customer, name)
的表,一个汽车表CAR(id_car, model, num_doors, ...)
(id_customer和id_car是它们各自表的主键)。
现在,您创建表PURCHASE以将客户与CARS关联并创建FOREIGN KEYS ...问题是什么是最佳选择?
1.PURCHASE(id_customer, id_car, date_purchase) -> Primary keys are (id_customer, id_car). Foreign keys are (id_customer->CUSTOMER.id_customer and id_car->CAR.id_car).
2.PURCHASE(id, id_customer, id_car, date_purchase) -> Primary keys are (id), Foreign keys are (id_customer->CUSTOMER.id_customer and id_car->CAR.id_car).
我的问题是,考虑到数据库的效率和优化,最佳选择是1还是2。
最佳答案
对于多对多映射,请按照这种方式进行。
CREATE TABLE XtoY (
# No surrogate id for this table
x_id MEDIUMINT UNSIGNED NOT NULL, -- For JOINing to one table
y_id MEDIUMINT UNSIGNED NOT NULL, -- For JOINing to the other table
# Include other fields specific to the 'relation'
PRIMARY KEY(x_id, y_id), -- When starting with X
INDEX (y_id, x_id) -- When starting with Y
) ENGINE=InnoDB;
笔记:
缺少此表的AUTO_INCREMENT ID-给定的PK是“自然” PK;没有代孕的充分理由。
“ MEDIUMINT”-提醒您,应将所有INT设置得尽可能安全(较小⇒更快)。当然,这里的声明必须与链接表中的定义匹配。
“ UNSIGNED”-几乎所有INT都可以被声明为非负数
“ NOT NULL”-是的,不是吗?
“ InnoDB”-比MyISAM更有效,因为PRIMARY KEY与InnoDB中的数据集群在一起。
“ INDEX(y_id,x_id)”-主键使向一个方向有效;这使另一个方向高效。无需说“唯一”;这将在INSERT上花费更多的精力。
在二级索引中,说justINDEX(y_id)会起作用,因为它将隐式包含x_id。但是,我希望我希望“覆盖”索引更加明显。
见Cookbook on building indexes
关于mysql - 在数据库中创建新的主键的最佳选择是什么?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/30129233/