简体   繁体   English

Oracle SQL使用for循环删除重复项

[英]Oracle SQL delete duplicates with for loop

I was asked to do a query to remove all duplicates that involve these 6 fields as we want a unique key in this table. 我被要求做一个查询以删除涉及这6个字段的所有重复项,因为我们想要此表中的唯一键。

I need to leave the one with biggest ID on the table and delete all the other ones. 我需要在表上保留ID最大的一个,并删除所有其他ID。 I came up with the following code following the suggestion of using a for-loop to do it. 在提出使用for循环的建议之后,我提出了以下代码。

begin
  for rec in (
      select max(id), attribute, product, partner, pr_group, contact_person, branch, count(1) cnt
        from co_attribute
        where attribute = 100000034 and product = 100252046
        group by attribute, product, partner, pr_group, contact_person, branch
        having count(1) > 1
  ) loop
      delete from co_attribute
        where (attribute = rec.attribute
          or (attribute is null and rec.attribute is null))
          and (product = rec.product 
            or (product is null and rec.product is null))
          and (partner = rec.partner 
            or(partner is null and rec.partner is null))
          and (pr_group = rec.pr_group 
            or(pr_group is null and rec.pr_group is null))
          and (contact_person = rec.contact_person 
            or(contact_person is null and rec.contact_person is null))
          and (branch = rec.branch 
            or(branch is null and rec.branch is null))
          and (max(id) < rec.id)
          ;
      dbms_output.put_line(
  'Deleting duplicates '            || 
  ' |attribute: '    || rec.attribute     || 
  ', product: '      || rec.product     ||
  ', partner: '      || rec.partner     ||
  ', pr_group: '     || rec.pr_group    ||
  ', contact_person: ' || rec.contact_person  ||
  ', branch: '     || rec.branch        ||
  ', id: '       || rec.id          ||
  ', deleting row: '   || sql%rowcount
  );
  end loop;
end;
/

The where in the select is just so I don't mess up the entire DB while testing this script. 选择中的位置只是为了在测试此脚本时不会弄乱整个数据库。 This gives me the following errors: 这给了我以下错误:

Error report -
ORA-06550: line 22, column 15:
PL/SQL: ORA-00934: group function is not allowed here
ORA-06550: line 9, column 7:
PL/SQL: SQL Statement ignored
06550. 00000 -  "line %s, column %s:\n%s"
*Cause:    Usually a PL/SQL compilation error.
*Action:

So I have two questions: first is, how do I solve this issue and is this the most effective way? 因此,我有两个问题:首先是如何解决这个问题,这是最有效的方法吗?

edit: removed the id field inside group by 编辑:删除分组依据内的ID字段

You may use below statement to leave the one with biggest ID on the table and delete all the other ones : 您可以使用以下语句在表上保留ID最大的一个,并删除所有其他ID:

delete co_attribute a
 where
   a.id <
   any (select b.id
          from co_attribute b
         where (a.attribute = b.attribute or (a.attribute is null and b.attribute is null))
           and (a.product = b.product or (a.product is null and b.product is null))
           and (a.partner = b.partner or (a.partner is null and b.partner is null))
           and (a.pr_group = b.pr_group or (a.pr_group is null and b.pr_group is null))
           and (a.contact_person = b.contact_person or (a.contact_person is null and b.contact_person is null))
           and (a.branch = b.branch or (a.branch is null and b.branch is null))
        );

I fixed it following a part of the comments and a few changes suggested over here! 我根据部分评论和此处的一些建议进行了修正! First I changed max(id) to max(id) maxid and also max(id) < rec.id to id < rec.maxid since maxid is part of rec and not of the delete query! 首先,我将max(id)更改为max(id) maxid并将max(id) < rec.idid < rec.maxid因为maxidrec一部分,而不是删除查询的一部分!

Thanks a lot for the help! 非常感谢您的帮助!

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM