我会为此在多个步骤。一步完成的大量删除操作让我感到非常紧张 - 如果您犯了一个错误,该怎么办?没有sql'undo'语句。
-- Setup the data
DROP Table foo;
DROP Table bar;
DROP Table bat;
DROP Table baz;
CREATE TABLE foo (
id int(11) NOT NULL,
SchemeName varchar(50),
SchemeNumber varchar(15),
PRIMARY KEY (id)
);
insert into foo values (714, 'Malcolm', 'ABC123');
insert into foo values (80, 'Malcolm', 'ABC123');
insert into foo values (96, 'Malcolms Scheme', 'ABC123');
insert into foo values (101, 'Malcolms Scheme', 'ABC123');
insert into foo values (98, 'Malcolms Scheme', 'DEF888');
insert into foo values (654, 'Another Scheme ', 'BAR876');
insert into foo values (543, 'Whatever Scheme ', 'KJL111');
-- Find all the records that have dups, find the longest one
create table bar as
select max(length(SchemeName)) as max_length, SchemeNumber
from foo
group by SchemeNumber
having count(*) > 1;
-- Find the one we want to keep
create table bat as
select min(a.id) as id, a.SchemeNumber
from foo a join bar b on a.SchemeNumber = b.SchemeNumber
and length(a.SchemeName) = b.max_length
group by SchemeNumber;
-- Select into this table all the rows to delete
create table baz as
select a.id from foo a join bat b where a.SchemeNumber = b.SchemeNumber
and a.id != b.id;
这会为您提供一个只包含要删除的行的记录的新表。
现在检查这些,并确保它们只包含要删除的行。通过这种方式,您可以确保在执行删除操作时,您确切地知道将会发生什么。它也应该很快。
然后,当您准备好时,使用此命令使用此命令删除行。
delete from foo where id in (select id from baz);
这似乎是更多的工作,因为不同的表,但它更安全,可能与其他方式一样快。另外,您可以在任何步骤中停止并确保在执行任何实际删除之前数据是您想要的。
不住那些有回答 - 请看我的更新! – 2010-10-06 17:36:13
您的数据在Jet/ACE或SQL Server中?如果前者,为什么你用SQL Server术语给你的数据类型?例如,Jet/ACE不支持BIGINT。数据在SQL Server中的事实将是一个重要的细节,因为它意味着SQL方言是不同的。或者您正在通过ODBC访问它,这对选择最佳任务方式具有各种含义。 – 2010-10-08 02:18:42
它在Access中,是的。抱歉。我更习惯于SQL Server,因此以这种形式提供了数据。我会改变它来说清楚。 – 2010-10-08 08:04:53