从greenplum表中删除真正的重复项

问题描述 投票:0回答:1

我试图从表中删除真正的重复项。我过去已经多次删除了dupes,但我无法弄清楚我的语法有什么问题。

我的代码 -

DELETE 
FROM   my_table_name 
WHERE  ( 
              column1, column2, column3, column4, column5, column6, column7, column8, column9) IN
       ( 
                SELECT   Row_number() OVER( partition BY column1, column2,column3, column4,column5,column6,column7,column8 ORDER BY column2 DESC, column3 ASC ) AS row_num,
                         column1, 
                         column2, 
                         column3, 
                         column4, 
                         column5, 
                         column6, 
                         column7, 
                         column8, 
                         column9 
                FROM     my_table_name 
                WHERE    column1='some_value') a 
WHERE  row_num=2;

错误

********** Error **********

ERROR: syntax error at or near ""a""
SQL state: 42601
Character: 1607

我可以看到错误是创建别名子查询。但是我无法确定这里有什么问题。

任何帮助表示赞赏


编辑1 - 如果我删除了一个,我得到以下错误

********** Error **********

ERROR: syntax error at or near "where"
SQL state: 42601
Character: 1608
sql duplicates greenplum
1个回答
0
投票

如果您有重复的行,则不能只删除单个命令中的所有记录。您必须删除所有重复项,然后为每个重复行只插入一个版本或构建新表(首选)而不重复。

让我们从首选方法开始,即创建一个没有重复项的新表。该解决方案以尽可能最有效的方式利用磁盘空间,而不是使用碎片表。

例:

create table foo
(id int, fname text)
with (appendonly=true)
distributed by (id);

插入一些重复的数据:

insert into foo values (1, 'jon');
insert into foo values (1, 'jon');
insert into foo values (2, 'bill');
insert into foo values (2, 'bill');
insert into foo values (3, 'sue');
insert into foo values (4, 'ted');
insert into foo values (4, 'ted');
insert into foo values (4, 'ted');
insert into foo values (4, 'ted');

创建没有重复项的表的新版本:

create table foo_new with (appendonly=true) as
select id, fname
from (
    select row_number() over (partition by id) as row_num, id, fname
    from foo
    ) as sub
where sub.row_num = 1
distributed by (id);

现在重命名表格:

alter table foo rename to foo_old;
alter table foo_new rename to foo;

第二种方法是使用DELETE,但您会发现它需要更多步骤才能完成。

首先,使用要删除的ID创建临时表。您通常没有在Greenplum中强制执行主键,但您仍然具有逻辑PK。 customer_id,product_id等列都在您的数据中。因此,首先根据PK找到重复项。

drop table if exists foo_pk_delete;
create temporary table foo_pk_delete with (appendonly=true) as
select id
from foo
group by id
having count(*) > 1
distributed by (id);

接下来,获取每个副本的整行,但只有一个版本。

drop table if exists foo_dedup;
create temporary table foo_dedup with (appendonly=true) as
select id, fname
from (
    select row_number() over (partition by f.id) as row_num, f.id, f.fname
    from foo f 
    join foo_pk_delete fd on f.id = fd.id
    ) as sub
where sub.row_num = 1
distributed by (id);

现在您可以删除重复项:

delete 
from foo f
using foo_pk_delete fk 
where f.id = fk.id;

然后,您可以将重复数据删除的数据插回到表中。

insert into foo (id, fname)
select id, fname from foo_dedup;

在数据操作之后,您需要对表进行抽真空。

vacuum foo;
© www.soinside.com 2019 - 2024. All rights reserved.