如何删除包含其他表的外键的表中的行

时间:2010-09-07 05:54:47

标签: sql sql-server sql-server-2008

假设有一个包含主键的主表,另一个表包含该主表的外键。因此,如果我们删除主表行,它也会删除子表。

如何撰写此查询?

5 个答案:

答案 0 :(得分:20)

从您的问题来看,我认为您可以安全地假设CASCADING DELETES已开启 在这种情况下所需要的只是

DELETE FROM MainTable
WHERE PrimaryKey = ???

您的数据库引擎将负责删除相应的引用记录。

答案 1 :(得分:19)

首先,作为一次性数据清理练习,删除孤立的行,例如

DELETE 
  FROM ReferencingTable 
 WHERE NOT EXISTS (
                   SELECT * 
                     FROM MainTable AS T1
                    WHERE T1.pk_col_1 = ReferencingTable.pk_col_1
                  );

其次,作为一次性模式更改练习,将ON DELETE CASCADE引用操作添加到引用表上的外键,例如

ALTER TABLE ReferencingTable DROP 
   CONSTRAINT fk__ReferencingTable__MainTable;

ALTER TABLE ReferencingTable ADD 
   CONSTRAINT fk__ReferencingTable__MainTable 
      FOREIGN KEY (pk_col_1)
      REFERENCES MainTable (pk_col_1)
      ON DELETE CASCADE;

然后,永久地,当引用的行被删除时,引用表中的行将被自动删除。

答案 2 :(得分:8)

您可以使用delete cascade选项更改外键约束,如下所示。这将删除与主表行相关的chind表行。

ALTER TABLE MasterTable
ADD CONSTRAINT fk_xyz 
FOREIGN KEY (xyz) 
REFERENCES ChildTable (xyz) ON DELETE CASCADE 

答案 3 :(得分:4)

如果要删除多行,并且不想更改表的结构 你可以使用光标。 1 - 首先需要选择要删除的行(在游标中) 2 - 然后对于光标中的每一行,删除引用行,然后删除它自己的行。

例如:

--id is primary key of MainTable
    declare @id int
    set @id = 1
    declare theMain cursor for select FK from MainTable where MainID = @id
    declare @fk_Id int
    open theMain
    fetch next from theMain into @fk_Id
    while @@fetch_status=0
    begin
        --fkid is the foreign key 
        --Must delete from Main Table first then child.
        delete from MainTable where fkid = @fk_Id
        delete from ReferencingTable where fkid = @fk_Id
        fetch next from theMain into @fk_Id
    end
    close theMain
    deallocate theMain

希望是有用的

答案 4 :(得分:-2)

需要将外键选项设置为删除级联 ... 在包含外键列的表中....需要在创建表时设置或稍后使用ALTER表

添加