2

私は次のテーブルを持っています:

tweets               retweets
-----------------    ----------------
user_id  retweets    user_id (etc...)
-----------------    ----------------
1        0           1
2        0           1
                     1
                     2
                     2

ユーザーごとのリツイート数をカウントし、それに応じてtweets.retweetsを更新したいと思います。

UPDATE users 
SET retweets = (
  SELECT COUNT(*) FROM retweets WHERE retweets.user_id = users.user_id
)

このクエリを2回実行しましたが、タイムアウトします(それほど大きくないテーブルで)。私のクエリは絞り込まれていますか?

UPDATESQL Fiddleも参照してください(ただし、ステートメントは許可されていないようです): http ://www.sqlfiddle.com/#!2/f591e/1

4

2 に答える 2

2

このソリューションは、各ユーザーのツイートの数を取得するためにサブクエリを使用するよりもはるかに高速である必要があります(相関サブクエリはユーザーごとに実行されます)。

UPDATE users a
LEFT JOIN
(
    SELECT user_id, COUNT(1) AS retweet_count
    FROM retweets
    GROUP BY user_id
) b ON a.user_id = b.user_id
SET a.retweets = COALESCE(b.retweet_count, 0)
于 2012-07-21T20:58:53.560 に答える
1

リツイートテーブルが動的に変化しない場合は、最初にデータを収集してから、次のように宛先テーブルを更新しないでください。

create table retweets_hist AS SELECT COUNT(*) AS retweets,user_id FROM retweets group by user_id;

それから

UPDATE users 
SET retweets = NVL(
  SELECT retweets FROM retweets_hist WHERE retweets_hist.user_id = users.user_id
),0)

動的な場合は、トリガーを使用する方が良いと思います。

ここでの主な問題は、リツイートを数えたことがないユーザーがいる場合、リツイートに時間がかかることです。

あなたの質問に答えて、はいカウントはほんの少しかかりますが、存在しなかったものをカウントするには時間がかかります!これが問題です!

これがより良いタイミングになるかもしれません:

 UPDATE users 
    SET retweets = NVL(
                       SELECT retweets 
                         FROM retweets 
                        WHERE retweets.user_id = users.user_id),0)
  WHERE EXISTS(select * 
                 FROM retweets 
                WHERE retweets.user_id = users.user_id)

ただし、リツイートをゼロに更新する必要はありません。

**キーワードEXISTSはOracleにありますmysqlがそれをサポートしているかどうかはわかりません

于 2012-07-19T19:56:19.353 に答える