1

好的,这是我的两个有冲突的表:

CREATE TABLE visit_physician (
   visit_id INT(11) UNSIGNED NOT NULL,
   physician_id INT(11) UNSIGNED NOT NULL,
   physician_role INT(11) UNSIGNED NOT NULL,
   PRIMARY KEY(visit_id, physician_id)
);

CREATE TABLE physician_role (
   id INT(11) UNSIGNED NOT NULL AUTO_INCREMENT KEY,
   name VARCHAR(50) NOT NULL,
   UNIQUE(name)
);

ALTER TABLE visit_physician
ADD CONSTRAINT FK_roleid
FOREIGN KEY (physician_role) REFERENCES physician_role(id)
ON UPDATE CASCADE
ON DELETE CASCADE;

医生角色和 id 是相同的数据类型和大小以及一切.. 那么为什么不创建呢?我的其他外键分配没有问题..

4

2 回答 2

2

我在 MySQL 5.5.29 上测试了你的语句,它们运行良好。请注意,两个表都必须使用 InnoDB 存储引擎才能支持外键。如果不是,MySQL 将解析但忽略这些约束的声明。

在我的实例中,默认存储引擎是 InnoDB。您的 CREATE TABLE 语句未指定存储引擎,因此它们将使用默认值。检查您的环境中的默认存储引擎是什么:

mysql> show global variables like 'default_storage_engine';
+------------------------+--------+
| Variable_name          | Value  |
+------------------------+--------+
| default_storage_engine | InnoDB |
+------------------------+--------+

使用 .检查表使用的存储引擎SHOW TABLE STATUS LIKE '%physician%'。查看输出的 Engine 列:

+-----------------+--------+---------+------------+------+----------------+-------------+-----------------+--------------+-----------+----------------+---------------------+-------------+------------+-------------------+----------+----------------+---------+
| Name            | Engine | Version | Row_format | Rows | Avg_row_length | Data_length | Max_data_length | Index_length | Data_free | Auto_increment | Create_time         | Update_time | Check_time | Collation         | Checksum | Create_options | Comment |
+-----------------+--------+---------+------------+------+----------------+-------------+-----------------+--------------+-----------+----------------+---------------------+-------------+------------+-------------------+----------+----------------+---------+
| physician_role  | InnoDB |      10 | Compact    |    0 |              0 |       16384 |               0 |        16384 |         0 |              1 | 2013-02-25 15:56:26 | NULL        | NULL       | latin1_swedish_ci |     NULL |                |         |
| visit_physician | InnoDB |      10 | Compact    |    0 |              0 |       16384 |               0 |        16384 |         0 |           NULL | 2013-02-25 15:56:26 | NULL        | NULL       | latin1_swedish_ci |     NULL |                |         |
+-----------------+--------+---------+------------+------+----------------+-------------+-----------------+--------------+-----------+----------------+---------------------+-------------+------------+-------------------+----------+----------------+---------+

如果引擎是 MyISAM 或其他存储引擎,则可能无法创建约束。

如果要将存储引擎更改为 InnoDB,可以这样做:

mysql> ALTER TABLE visit_physician ENGINE=InnODB;
mysql> ALTER TABLE physician_role ENGINE=InnODB;

然后您应该能够重新执行约束的创建。但是,如果表中已经包含不满足约束的数据,则可能会导致问题。

但在进行任何此类更改之前,我鼓励您测试您的应用程序是否仍可与不同的存储引擎一起使用。它很可能会正常工作,但测试总是一个好主意。


当您尝试添加外键时会发生什么?如果它给出这样的错误:

ERROR 1452 (23000): Cannot add or update a child row: a foreign key constraint 
fails (`test`.`#sql-c67_52`, CONSTRAINT `FK_roleid` FOREIGN KEY (`physician_role`) 
REFERENCES `physician_role` (`id`) ON DELETE CASCADE ON UPDATE CASCADE)

那么您可能在表中已经有一些不满足约束的值。

关于存储引擎和数据类型的其他可能性也可能导致错误,但我们已经排除了,因为您说表都是 InnoDB 并且数据类型看起来相同,并且在我测试时它可以工作。

于 2013-02-26T00:04:49.020 回答
0

我认为这可能与一张表上的两个外键约束有关,但我在创建表时添加了它们,所以它是这样的:

CREATE TABLE visit_physician (
   visit_id INT(11) UNSIGNED NOT NULL,
   physician_id INT(11) UNSIGNED NOT NULL,
   physician_role INT(11) UNSIGNED NOT NULL,
   PRIMARY KEY(visit_id, physician_id),
   CONSTRAINT FOREIGN KEY (physician_id) REFERENCES user (id) ON DELETE CASCADE ON UPDATE CASCADE,
   CONSTRAINT FOREIGN KEY (physician_role) REFERENCES physician_role (id) ON DELETE CASCADE ON UPDATE CASCADE
);

以防万一有人遇到我遇到的奇怪问题..

于 2013-02-26T01:37:57.397 回答