如何删除MySQL中具有相似模式的条目

时间:2012-07-29 19:55:21

标签: mysql

我有一个列可能包含这样的条目: abc.yahoo.com efg.yshoo.com hij.yahoo.com

我需要删除所有重复项并仅保留一个,因为我不需要其他副本。如果我知道第二部分(例如:yahoo.com),这样的命令可以很容易地完成,但我的问题是部分(yahoo.com)没有修复。我可能有以下条目: abc.msn.com efg.msn.com hij.msn.com

我想立即处理所有这些案件。这可能吗?

2 个答案:

答案 0 :(得分:0)

这假设您只想在列上的第一个.然后组中取出字母:

DELETE a FROM tbl a
LEFT JOIN
(
    SELECT   MIN(id) AS id
    FROM     tbl
    GROUP BY SUBSTRING(column, LOCATE('.', column))
) b ON a.id = b.id
WHERE b.id IS NULL

其中id是您的主键列名称,column是包含要分组的值的列。

这也会考虑像xxx.co.uk这样的域,最后你有两个部分。

确保备份当前数据或在交易中运行此操作(如果不符合您的需要,您可以ROLLBACK;)。

编辑:如果在删除重复项后,您想要在第一个.之前用*替换字母,则只需使用:

UPDATE tbl
SET column = CONCAT('*', SUBSTRING(column, LOCATE('.', column)))

答案 1 :(得分:0)

要删除重复项,可以使用

DELETE FROM your_table t1
LEFT JOIN
(
    SELECT   MIN(id) AS id
    FROM     your_table 
    GROUP BY SUBSTRING_INDEX(REVERSE(col), '.', 2)
) t2 ON t2.id = t1.id
WHERE b.id IS NULL

如果您需要为其创建UNIQUE约束,则可以执行以下操作

1.添加另一个字段以保存域值

ALTER TABLE your_table ADD COLUMN `domain` VARCHAR(100) NOT NULL DEFAULT '';

2.使用正确的值

更新它
UPDATE your_table set domain = REVERSE(SUBSTRING_INDEX(REVERSE(col), '.', 2));

3.添加唯一约束

ALTER IGNORE TABLE your_table ADD UNIQUE domain (domain);

4.在插入之前和更新trggers之前添加以设置域列

DELIMITER $$

CREATE TRIGGER `your_trigger` BEFORE INSERT ON `your_table ` FOR EACH ROW 
BEGIN
    set new.domain = REVERSE(SUBSTRING_INDEX(REVERSE(new.col1), '.', 2));
END$$


CREATE TRIGGER `your_trigger` BEFORE UPDATE ON `your_table ` FOR EACH ROW 
BEGIN
    set new.domain = REVERSE(SUBSTRING_INDEX(REVERSE(new.col1), '.', 2));
END$$

DELIMITER ;

注意:这假定域名是以'。'分隔的最后2个单词,它不适用于ebay.co.uk等域。为此,您可能需要创建一个存储函数,该函数返回给定主机的域并使用它而不是REVERSE(SUBSTRING_INDEX...