1

我有一张这样的桌子:

桌子

id
=====
1
1
2
2
6
6
7
5
5
9

除了创建新表之外,我还需要删除重复项。一种方法是:

create table_new (select distinct id from table )

是否有删除重复项的删除命令?

4

7 回答 7

1

恕我直言,在普通情况下(Ansi SQL)你不能这样做,因为没有唯一的关键字段,你不能区分一行和另一行,所以你不能删除它。

但在 MySQL 中,您可以运行这个 UGLY 查询。它使用@S sting 来累积 ID,所以不要在大桌子上使用它:

set @S:=',';
delete from t 
where if(LOCATE(CONCAT(',',ID,','),@S)>0,'del',@S:=CONCAT(@S,ID,','))='del'
于 2012-08-08T15:16:41.363 回答
0

示例代码

http://sqlfiddle.com/#!3/56182/2

于 2012-08-08T07:01:08.450 回答
0

我不确定是否有任何直接实现,但这里有一个您可能感兴趣的函数实现。

function RemoveDuplicates($TableName, $UniqueFieldName, $IDFieldName, $FirstFoundIDValue)
{
    $Query =    "DELETE  FROM ".$TableName." ".
                "WHERE    ".$IDFieldName." IN ".
                "( SELECT a.".$IDFieldName." ".
                    "FROM ".$TableName." a, ".$TableName." b ".
                    "WHERE (a.".$UniqueFieldName." = b.".$UniqueFieldName.") ".
                    "AND (a.".$IDFieldName." > ".$FirstFoundIDValue.") ".
                    "GROUP BY a.".$IDFieldName." ".
                    "HAVING COUNT(a.".$UniqueFieldName.") > 1 ".
                ")";
    db_query($Query);

// Example Use:            
// delete  from tblps_CommEquip 
// where PSID in    
// ( select a.PSID from tblps_CommEquip a, tblps_CommEquip b     
//      where    (a.CommEquipType = b.CommEquipType) 
//      AND (a.PSID > 80)    
//      group by a.PSID 
//      having count(a.CommEquipType) > 1
// )
} 
于 2012-08-08T07:02:40.363 回答
0

第一次上谷歌:

http://support.microsoft.com/kb/139444/en-us?fr=1

本文描述了使用临时表来保存唯一记录,清除原始表并将唯一记录添加回其中,您可能可以通过编写一些存储过程来做到这一点,但我想您只需要这样做一次吗?然后我会按照描述的方法去。此外,为了防止将来出现问题,请对该字段使用唯一键或主键约束,这样就不可能有 2 条记录具有相同的值。

于 2012-08-08T06:51:19.403 回答
0

您可以使用 cte:

;WITH cte
     AS (SELECT ROW_NUMBER() OVER (PARTITION BY ID 
                                       ORDER BY ( SELECT 0)) RN
         FROM   #MyTable)
DELETE FROM cte
WHERE  RN > 1

这将避免为您的不同记录创建临时表或保留表的需要。如果您有可能包含重复值的其他列,则可以IDPARTITION BY表达式的后面添加它们。

尽管我会担心您为什么有重复的 ID 值。

  • 如果这是一个行 ID,那么我建议使用 IDENTITY 并自动增加 ID。
  • 如果它是一个项目或参考 ID,那么我会尽量避免添加重复项(这可能是完全错误的,具体取决于您的结构)
于 2012-08-08T06:52:01.277 回答
0

删除所有重复项的单个查询(在 Oracle 中测试)

从 my_table 中删除 rowid 不在(按 id 从 temp_table 组中选择 min(rowid));

解释:

默认情况下,Oracle 给每一行一个 rowid(我相信其他数据库有相同或相似的东西)。

我们先看一下内部查询。Group by 子句根据一些标准对行进行分组,在我们的例子中是 Id。我们也可以基于多个列进行分组(按 col1、col2 分组)。当我们说 min(rowid) 时,我们只是确保它返回一个 rowid,以防多行具有重复的列。

外部删除查询很简单,它只是从表中删除我们内部查询未返回的所有其他内容(重复项)

于 2012-08-08T06:55:17.997 回答
0

删除重复行的最佳方法是提供一个唯一标识表中每条记录的主键列。

于 2012-08-08T10:10:56.990 回答