删除加入MySQL

时间:2009-03-17 01:44:06

标签: mysql

以下是创建表格的脚本:

CREATE TABLE clients (
   client_i INT(11),
   PRIMARY KEY (client_id)
);
CREATE TABLE projects (
   project_id INT(11) UNSIGNED,
   client_id INT(11) UNSIGNED,
   PRIMARY KEY (project_id)
);
CREATE TABLE posts (
   post_id INT(11) UNSIGNED,
   project_id INT(11) UNSIGNED,
   PRIMARY KEY (post_id)
);

在我的PHP代码中,删除客户端时,我想删除所有项目帖子:

DELETE 
FROM posts
INNER JOIN projects ON projects.project_id = posts.project_id
WHERE projects.client_id = :client_id;

帖子表没有外键client_id,只有project_id。我想删除已通过client_id

的项目中的帖子

目前无效,因为没有帖子被删除。

14 个答案:

答案 0 :(得分:1164)

您只需要指定要删除posts表中的条目:

DELETE posts
FROM posts
INNER JOIN projects ON projects.project_id = posts.project_id
WHERE projects.client_id = :client_id

编辑:有关详细信息,请参阅this alternative answer

答案 1 :(得分:73)

由于您要选择多个表,因此要删除的表不再明确。您需要选择

DELETE posts FROM posts
INNER JOIN projects ON projects.project_id = posts.project_id
WHERE projects.client_id = :client_id

在这种情况下,table_name1table_name2是同一个表格,因此可以使用:

DELETE projects FROM posts INNER JOIN [...]

如果您愿意,甚至可以从两个表中删除:

DELETE posts, projects FROM posts INNER JOIN [...]

请注意order bylimit don't work for multi-table deletes

另请注意,如果声明表的别名,则在引用表时必须使用别名:

DELETE p FROM posts as p INNER JOIN [...]

Contributions from Carpetsmoker and etc

答案 2 :(得分:48)

或者同样的事情,稍微不同(IMO友好)语法:

DELETE FROM posts 
USING posts, projects 
WHERE projects.project_id = posts.project_id AND projects.client_id = :client_id;
BTW,使用连接的mysql几乎总是比子查询更快......

答案 3 :(得分:39)

您也可以像这样使用ALIAS它只是在我的数据库中使用它! t表是需要删除的!

DELETE t FROM posts t
INNER JOIN projects p ON t.project_id = p.project_id
AND t.client_id = p.client_id

答案 4 :(得分:24)

我更习惯于子查询解决方案,但我还没有在MySQL中尝试过:

DELETE  FROM posts
WHERE   project_id IN (
            SELECT  project_id
            FROM    projects
            WHERE   client_id = :client_id
        );

答案 5 :(得分:11)

MySQL使用JOIN删除记录

通常在SELECT语句中使用INNER JOIN从表中选择具有其他表中相应记录的记录。我们还可以使用带有DELETE语句的INNER JOIN子句来删除表中的记录以及其他表中的相应记录,例如,要删除满足特定条件的T1和T2表中的记录,请使用以下语句: / p>

DELETE T1, T2
FROM T1
INNER JOIN T2 ON T1.key = T2.key
WHERE condition

请注意,您将表名T1和T2放在DELETE和FROM之间。如果省略T1表,DELETE语句只删除T2表中的记录,如果省略T2表,则只删除T1表中的记录。

连接条件T1.key = T2.key指定T2表中需要删除的相应记录。

WHERE子句中的条件指定需要删除T1和T2中的哪些记录。

答案 6 :(得分:8)

单表删除:

要从posts表中删除条目:

DELETE ps 
FROM clients C 
INNER JOIN projects pj ON C.client_id = pj.client_id
INNER JOIN posts ps ON pj.project_id = ps.project_id
WHERE C.client_id = :client_id;

要从projects表中删除条目:

DELETE pj 
FROM clients C 
INNER JOIN projects pj ON C.client_id = pj.client_id
INNER JOIN posts ps ON pj.project_id = ps.project_id
WHERE C.client_id = :client_id;

要从clients表中删除条目:

DELETE C
FROM clients C 
INNER JOIN projects pj ON C.client_id = pj.client_id
INNER JOIN posts ps ON pj.project_id = ps.project_id
WHERE C.client_id = :client_id;

多个表格删除:

为了从联接结果中删除多个表中的条目,您需要在DELETE之后以逗号分隔列表指定表名:

假设您要删除特定客户的所有三个表(postsprojectsclients)中的条目:

DELETE C,pj,ps 
FROM clients C 
INNER JOIN projects pj ON C.client_id = pj.client_id
INNER JOIN posts ps ON pj.project_id = ps.project_id
WHERE C.client_id = :client_id

答案 7 :(得分:7)

尝试如下:

DELETE posts.*,projects.* 
FROM posts
INNER JOIN projects ON projects.project_id = posts.project_id
WHERE projects.client_id = :client_id;

答案 8 :(得分:4)

使用优于使用IN的子选择删除的另一种方法是WHERE EXISTS

DELETE  FROM posts
WHERE   EXISTS ( SELECT  1 
                 FROM    projects
                 WHERE   projects.client_id = posts.client_id);

使用此代替联接的一个原因是DELETE JOIN禁止使用LIMIT。如果您希望在块中删除以便不生成完整的表锁,可以使用此LIMIT方法添加DELETE WHERE EXISTS

答案 9 :(得分:4)

mysql> INSERT INTO tb1 VALUES(1,1),(2,2),(3,3),(6,60),(7,70),(8,80);

mysql> INSERT INTO tb2 VALUES(1,1),(2,2),(3,3),(4,40),(5,50),(9,90);

从一个表中删除记录:

mysql> DELETE tb1 FROM tb1,tb2 WHERE tb1.id= tb2.id;

从两个表中删除记录:

mysql> DELETE tb2,tb1 FROM tb2 JOIN tb1 USING(id);

答案 10 :(得分:1)

如果加入对您不起作用,您可以尝试此解决方案。它用于在不使用外键+特定条件时从t1删除孤立记录。即它删除table1中的记录,这些记录具有空字段“code”,并且没有table2中的记录,通过字段“name”匹配。

delete table1 from table1 t1 
    where  t1.code = '' 
    and 0=(select count(t2.name) from table2 t2 where t2.name=t1.name);

答案 11 :(得分:0)

试试这个,

DELETE posts.*
FROM posts
INNER JOIN projects ON projects.project_id = posts.project_id
WHERE projects.client_id = :client_id

答案 12 :(得分:0)

一种解决方案是使用子查询

DELETE FROM posts WHERE post_id in (SELECT post_id FROM posts p
INNER JOIN projects prj ON p.project_id = prj.project_id 
INNER JOIN clients c on prj.client_id = c.client_id WHERE c.client_id = :client_id 
);

子查询返回需要删除的ID;这三个表都使用联接进行连接,只有符合过滤条件的记录才被删除(在您的情况下,即where子句中的client_id)。

答案 13 :(得分:-3)

- 请注意,您不能在需要删除的表格上使用别名

DELETE tbl_pagos_activos_usuario
FROM tbl_pagos_activos_usuario, tbl_usuarios b, tbl_facturas c
Where tbl_pagos_activos_usuario.usuario=b.cedula
and tbl_pagos_activos_usuario.cod=c.cod
and tbl_pagos_activos_usuario.rif=c.identificador
and tbl_pagos_activos_usuario.usuario=c.pay_for
and tbl_pagos_activos_usuario.nconfppto=c.nconfppto
and NOT ISNULL(tbl_pagos_activos_usuario.nconfppto)
and c.estatus=50