删除除了一些行之外的所有行 - Oracle

时间:2009-11-27 13:06:27

标签: sql oracle

我想从表中删除一组行。我可以决定哪些行需要删除。只有当行数大于5(基于条件)时,我才会从表中删除行。

考虑这个样本数据

ID--Col1--Col2--
1   A      X
2   A      X
3   A      X
4   A      X
5   A      X
6   A      X
7   A      X
8   A      X
9   A      X
10   A      X
11   B      X
12   B      X
13   B      X
14   B      X
15   C      X
16   C      X
17   C      X
18   D      X
19   D      X

我想要删除5行{*,A,X},我需要保留5行(无论哪一行)。我不会删除B,C& D因为它们的数量小于5。

delete from tableA
 --- I can decide on the rows to delete based on two conditions.
 where col1 = someCondition
   and col2 = someOtherCondition
   and rownum > 5 --- This dint work. I checked.

我想也许我需要编程。任何建议都非常感谢。

5 个答案:

答案 0 :(得分:9)

这将删除col1和col2的每个唯一组合的所有行,而不是rowid排序的前五个

delete from my_table
where rowid in
  (
  select rowid
  from
    (
    select rowid,
           row_number() over (partition by col1, col2 order by rowid) rownumber
    from   my_table
    )
  where rownumber > 5
  )
/

答案 1 :(得分:7)

这将删除除了满足Col1和Col2两个条件的20行之外的所有行:

DELETE FROM tableA
 WHERE ROWID NOT IN (SELECT ROWID
                       FROM tableA
                      WHERE col1 = someCondition
                        AND col2 = someOtherCondition
                        AND rownum <= 20)

如果您的数据集非常大,以下内容可能会更快:

CREATE tableTemp as 
SELECT *
  FROM tableA
 WHERE col1 = someCondition
   AND col2 = someOtherCondition
   AND rownum <= 20;

TRUNCATE tableA;

INSERT INTO tableA (SELECT * FROM tableTemp);

如果您需要在操作期间访问数据,请用DELETE替换truncate。

答案 2 :(得分:2)

每组最多保留5个:

delete mytable where rowid in
( select rowid from
  ( select rowid, row_number() over (partition by col1, col2 order by id) rn
    from mytable
  )
  where rn > 5
);

答案 3 :(得分:0)

ROWNUM&gt; 5不起作用,因为对于第一个受影响的行,ROWNUM始终为1;这个条件还包括“ROWNUM&gt; 5”部分,因此Oracle不可能找到适合该法案的行。

这可能有效:

delete from tableA
 --- I can decide on the rows to delete based on two conditions.
 where col1 = someCondition
   and col2 = someOtherCondition
   and rownum <= (select count(*) from tableA 
                    where col1 = someCondition
                      and col2 = someOtherCondition) - 5;

答案 4 :(得分:-1)

在表格中保留任意500行并删除其余行。

delete from tablenameX where rownum <= (select count(*) - 500 from tablenamex);

如果行数很小,则只建议使用sql。如果大,那么使用之前建议的创建临时表的方法。