2010-05-13 87 views
1

我有一个表是这样的:MySQL ::消除表中的冗余元素?

+-------+---------+------+-----+---------+-------+ 
| Field | Type | Null | Key | Default | Extra | 
+-------+---------+------+-----+---------+-------+ 
| v1 | int(11) | YES | MUL | NULL |  | 
| v2 | int(11) | YES | MUL | NULL |  | 
+-------+---------+------+-----+---------+-------+ 

有重复的在这个表中的巨大数额。例如,以下元素:

+------+------+ 
| v1 | v2 | 
+------+------+ 
| 1 | 2 | 
| 1 | 3 | 
| 1 | 4 | 
| 1 | 5 | 
| 1 | 6 | 
| 1 | 7 | 
| 1 | 8 | 
| 1 | 9 | 
| 2 | 1 | 
| 4 | 1 | 
| 5 | 1 | 
| 6 | 1 | 
| 7 | 1 | 
| 8 | 1 | 
| 9 | 1 | 
+------+------+ 

该表很大,有1540000个条目。要删除多余的条目(即得到一个只有(1,9)和(9,1)条目的表),我想用子查询来做,但有没有更好的方法来做到这一点?

回答

0

其实@Mark的方法也会起作用。我只是想出了另一种方法,并想知道我是否也能对此做出反馈。我测试了它,它似乎工作得很快。

SELECT v1,v2 FROM table WHERE v1<v2 UNION SELECT v2,v1 FROM table WHERE v1>v2; 

在这是正确的话,你总是可以创建一个新表:

CREATE TABLE newtable AS SELECT v1,v2 FROM edges WHERE v1<v2 UNION SELECT v2,v1 FROM edges WHERE v1>v2; 
0

警告:这些命令修改您的数据库。确保您有备份副本,以便您可以根据需要再次恢复数据。

您可以添加v1必须小于v2的要求,这会减少您的存储需求大约一半。您可以确保数据库中的所有行均满足此条件,并重新排序那些不相同的行,并在两者都有时删除其中一行。

这个查询将插入,你必须例如任何遗漏行(5,1),而不是(1,5):

INSERT INTO table1 
SELECT T1.v2, T1.v1 
FROM table1 T1 
LEFT JOIN table1 T2 
ON T1.v1 = T2.v2 AND T1.v2 = T2.v1 
WHERE T1.v1 > T1.v2 AND T2.v1 IS NULL 

然后这个查询删除你不想要的行,像( 5,1):

DELETE table1 WHERE v1 > v2 

您可能需要更改代码中添加此约束条件之前编程的其他位置。

+0

感谢您的时间。我只是想出了另一种方式并添加了它。我认为这两种方法基本上都使用相同的逻辑。你能让我知道你对我的解决方案的看法吗? – Legend 2010-05-13 19:42:29

+0

@传奇:你的方法是创建一个新表。我的方法修改了现有表中的数据。我们都有相同的基本思想:对数据进行重新排序,使得“v1 2010-05-13 19:45:41