2017-09-20 12 views
0

私は時には重複する行の値を持つテーブルを持っているので、最初のもの以外のものを更新し、それを重複としてフラグを立てたいと思います。現在、私はこれを使用していますが、それは非常に遅くなることができます。重複行にフラグを立てるためにMySQLの自己結合 - これを行うにはより良い方法ですか?

UPDATE _gtemp X 
    JOIN _gtemp Y 
    ON CONCAT(X.gt_spid, "-", X.gt_cov) = CONCAT(Y.gt_spid, "-", Y.gt_cov) 
    AND Y.gt_dna = 0 
    AND Y.gt_gtid < X.gt_gtid 
    SET X.gt_dna = 1; 

gt_spidは、数値IDで、gt_covはCHAR(3)です。私はgt_spidのインデックスとgt_spid、gt_covの2番目のインデックスを持っています。時には、このテーブルは25万行以上になることがありますが、30,000であってもそれは永遠に必要です。

これを実行するより良い方法はありますか?私は必要に応じてテーブルを変更することができます。

CREATE TABLE `_gtemp` (
    `gt_gtid` int(11) NOT NULL AUTO_INCREMENT, 
    `gt_group` varchar(10) DEFAULT NULL, 
    `gt_spid` int(11) DEFAULT NULL, 
    `gt_cov` char(3) DEFAULT NULL, 
    `gt_dna` tinyint(1) DEFAULT '0' 
PRIMARY KEY (`gt_gtid`), 
KEY `spid` (`gt_spid`), 
KEY `spidcov` (`gt_spid`,`gt_cov`) USING HASH 
) 
+1

以下のようなAND文でCONCATを交換する必要がある理由です、あなただけの全体のテーブル定義を投稿することができます。 – fancyPants

+1

テーブル内の適切な列に制約を設定して重複が作成されないようにするのはなぜですか? – ADyson

答えて

3

にインデックスを追加します。

あなたが代わりにあなたのテーブルを記述したテキストの山を掲示し、重要な部分を残しての

UPDATE 
    _gtemp X 
    JOIN 
    _gtemp Y 
    ON 
     X.gt_spid = Y.gt_spid 
    AND 
     X.gt_cov = Y.gt_cov 
    AND 
     Y.gt_dna = 0 
    AND 
     Y.gt_gtid < X.gt_gtid 
    SET X.gt_dna = 1; 
+0

ありがとう!私はCONCATと索引を読まなければならないでしょう - 私はそれを認識していませんでした! – Steve

1

あなたはCONCATONで句を排除し、次のようにANDに置き換えることができます。

また、ONからWHERE節に1つの制限が移されました。

あなたはCONCATを使用している方法は、MySQLのオプティマイザは、それは非常に遅い実行中のクエリで、その結果、インデックスだ失う可能gt_dna

UPDATE _gtemp X 
    JOIN _gtemp Y 
    ON X.gt_spid = Y.gt_spid 
    AND X.gt_cov = Y.gt_cov 
    AND Y.gt_dna = 0 
    SET X.gt_dna = 1 
    WHERE Y.gt_gtid < X.gt_gtid 
関連する問題