【问题标题】:Delete with "Join" in Oracle sql Query在 Oracle sql 查询中使用“加入”删除
【发布时间】:2012-09-22 05:33:46
【问题描述】:

我对 Oracle Sql 查询并不十分熟悉,因此我在从表中删除某些行时遇到问题,这些行必须满足包含另一个(连接)表的字段的约束。换句话说,我想编写一个查询来删除包括 JOIN 在内的行。

在我的情况下,我有一个表 ProductFilters 和另一个表 Products 加入字段 ProductFilters.productID = Products.ID。我想从ProductFilters 中删除ID 大于或等于200 的行,并且它们引用的产品名称为“Mark”(名称是产品中的一个字段)。

我想先了解一下 JOIN 在 Oracle 中的删除查询中是否可以接受。如果不是,我应该如何修改此查询以使其正常工作,因为在该表单上我收到一个错误:

DELETE From PRODUCTFILTERS pf 
where pf.id>=200 
And pf.rowid in 
(
     Select rowid from PRODUCTFILTERS 
     inner join PRODUCTS on PRODUCTFILTERS.PRODUCTID = PRODUCTS.ID 
     And PRODUCTS.NAME= 'Mark'
);       

【问题讨论】:

标签: sql oracle sql-delete


【解决方案1】:

最近学习了以下语法:

DELETE (SELECT *
        FROM productfilters pf
        INNER JOIN product pr
            ON pf.productid = pr.id
        WHERE pf.id >= 200
            AND pr.NAME = 'MARK')

我认为它看起来比其他提议的代码更干净。

【讨论】:

  • 此查询是仅从第一个表“productfilters”中删除行还是从两个表中删除行?
  • @IvanGerasimenko 它从两个表中删除行。
  • @KevinOrtman 如果对 FK 约束有级联删除操作,则为是,否则为否。 (看解释计划看哪一个,级联不会显示)
  • 如果你这样做select pf.*它只会删除productfilters?
  • @chillworld 是的。我测试了它。此外,这应该是公认的答案。远远优于现在。
【解决方案2】:

根据我在上面的评论中链接到的答案,这应该可行:

delete from
(
select pf.* From PRODUCTFILTERS pf 
where pf.id>=200 
And pf.rowid in 
  (
     Select rowid from PRODUCTFILTERS 
     inner join PRODUCTS on PRODUCTFILTERS.PRODUCTID = PRODUCTS.ID 
     And PRODUCTS.NAME= 'Mark'
  )
); 

delete from PRODUCTFILTERS where rowid in
(
select pf.rowid From PRODUCTFILTERS pf 
where pf.id>=200 
And pf.rowid in 
  (
     Select PRODUCTFILTERS.rowid from PRODUCTFILTERS 
     inner join PRODUCTS on PRODUCTFILTERS.PRODUCTID = PRODUCTS.ID 
     And PRODUCTS.NAME= 'Mark'
  )
); 

【讨论】:

  • 我尝试了第二个,但收到错误:“列定义不明确”。此外,我认为开始时的正确语法是 delete PRODUCTFILTERS 其中...“From”在删除查询中是多余的。
  • rowid 在没有别名的情况下是不明确的。对于带连接的删除,查询很好。
【解决方案3】:

在 where 子句中使用子查询。对于需要连接的删除查询,此示例将删除连接表“docx_document”中不匹配且“docs_documents”表中创建日期 > 120 天的行。

delete from docs_documents d
where d.id in (
    select a.id from docs_documents a
    left join docx_document b on b.id = a.document_id
    where b.id is null
        and floor(sysdate - a.create_date) > 120
 );

【讨论】:

    【解决方案4】:

    请使用子查询

    delete from productfilters
    where productid in (Select id from products where name='Mark') and Id>200;
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-04-11
      • 2017-03-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-10-22
      • 2021-06-20
      相关资源
      最近更新 更多