具有N:M关系的重复表(包括关系)

4
在处理一个现有的 web 应用程序(PHP/MySQL)时,我遇到了如下问题: 我有两个表存储名称和类型 ID。它们之间的关系为 N<---->N,我中间还有另一张表(见图片)。

Tables names and columns have been simplified, but it's pretty much it

我还有一张名为“category”的未列出图片的表。我需要做的是:将 id_category=1 的合同和客户复制到值相同的 id_category=3 的合同和客户中,同时复制它们之间的关系
到目前为止,我已经成功地将所有合同和客户分开复制,使用以下方法:
INSERT INTO contract (t_name, id_category) SELECT t_name,'3' WHERE id_category=2
INSERT INTO customer (t_name, id_category) SELECT t_name,'3' WHERE id_category=2

(“id”字段是自动递增的,这很好处理。)
但是关于复制关系,我无法解决问题。
附加信息:
- 使用临时表可以解决问题,但是不能修改现有表的结构。 - 合同可能有0到N个客户。 客户可能拥有0到N个合同。 - 我可以使用严格的MySQL或PHP来处理。

那个新表格具体代表什么? - Iberê
1
没有新的表格。我必须在已经存在的表格中进行复制。 - monsieur_h
1个回答

0

你说你不能改变表结构。如果可以的话,根据你所做的事情,我可能会建议不要对这些表进行反规范化(行重复)。

我也有点困惑,因为你说必须将具有 id_category = 1 的行和关系复制到 id_category = 3,但是你的示例查询却有 id_category = 2

无论如何,这个答案都适用。我会使用PHP和PDO。

$pdo = new PDO('mysql:host=?', $user, $passwd);
$stmtCustomers = $pdo->prepare("INSERT INTO customer (t_name, id_category)
   VALUES (t_name, ?) WHERE id_category = ?");
$stmtContracts = $pdo->prepare("INSERT INTO contract (t_name, id_category)
   VALUES (t_name, ?) WHERE id_category = ?");
$stmtRelation = $pdo->prepare("INSERT INTO customer_has_contract VALUES (?, ?)");

//Perform in a loop if needed
$pdo->beginTransaction();
$stmtCustomers->execute($target_cat_id, $origin_cat_id);
$cus_id = $pdo->lastInsertId();
$stmtContracts->execute($target_cat_id, $origin_cat_id);
$con_id = $pdo->lastInsertId();
$stmtRelation->execute($con_id, $cus_id);
$pdo->commit();

谢谢您的回答。关于分类:那是个打字错误。我的方法必须与任何给定的参数完成。(例如复制类别2到3,或1->4...)。关于SQL:$stmtRelation->execute($con_id, $cus_id);不会将每个客户与每个合同链接起来吗?那么零合同的客户怎么办?他们在您的解决方案中会得到一个合同。 - monsieur_h
@caffein 那个 execute 只会链接你插入的最后一个客户和合同。如果它是“0”或者查询由于某些原因无法插入,你可以跳过关系检查。这是可能的吗? - Explosion Pills
它是如何工作的:$stmtCustomers-execute() 将插入整个集合的重复客户,而 ->lastInsertId() 只会返回其中一个。我不理解。 - monsieur_h

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接