0

私がやろうとしているのは、次のチェックを行う1つのクエリを作成することです:

「yesnotmp」データベースに 2 つのテーブルがあります。msg_tすべてのメッセージを含む1 つが呼び出されsend_time、多くの列があります。statusphonesushi_sub_id

ここでは、昨日のすべての電話、sushi_sub_id レコードを取得しています。(そしてそれは動作します)

SELECT phone, sushi_sub_id FROM `yesnotmp`.`msg`
        LEFT JOIN `yesnotmp`.`msg_t` ON (`msg`.`id`=`msg_t`.`msg_id`)
        WHERE `msg_t`.`send_time` BETWEEN '2013-06-02' AND '2013-06-03' 
            AND `msg_t`.`status` = 'Failure.Provider.Connection'

私がやろうとしているのは、retryテーブルphoneで、同じものが挿入されたものsushi_sub_idとそうでないものがいくつあるかを確認することです。(このクエリは非常に時間がかかります)

SELECT 
    Sum(CASE WHEN (SELECT Count(*) FROM `retry` AS `rty` WHERE `rty`.`phone` = `msgs`.`phone` AND `rty`.`sushi_subscription_id`=`msgs`.`sushi_sub_id`) > 0 THEN 1 ELSE 0 END) AS `In_Retry`,
Sum(CASE WHEN (SELECT Count(*) FROM `retry` AS `rty` WHERE `rty`.`phone` = `msgs`.`phone` AND `rty`.`sushi_subscription_id`=`msgs`.`sushi_sub_id`) > 0 THEN 0 ELSE 1 END) AS `Not_In_Retry`
FROM 
    (SELECT phone, sushi_sub_id FROM `yesnotmp`.`msg`
        LEFT JOIN `yesnotmp`.`msg_t` ON (`msg`.`id`=`msg_t`.`msg_id`)
        WHERE `msg_t`.`send_time` BETWEEN '2013-06-02' AND '2013-06-03' 
            AND `msg_t`.`status` = 'Failure.Provider.Connection') AS `msgs`
4

2 に答える 2

3

私が提案するわずかな変更...各列の選択を介して合計するのではなく、単純に結合してそれらを直接カウントします。まず、Msg_T テーブルへの LEFT-JOIN ですが、Msg_T テーブルに WHERE 句を使用すると、強制的に INNER JOIN になります。

特定の日付とステータスの間のメッセージ時間アクティビティを探しています。クエリを最適化するために、(status, send_time) の MSG_T にインデックスを作成して、「Failure.Provider.Connection」に直接ジャンプし、次に問題の日付範囲に直接ジャンプできるようにします。

さて、再試行テーブル。再試行エントリがない可能性があるため、これはLEFT結合になる可能性があります(間違っている場合は修正してください)。

SELECT 
      msg_t.phone, 
      msg_t.sushi_sub_id,
      max( case when rty.phone is not null then 1 else 0 end ) as In_Retry,
      max( case when rty.phone is  null then 1 else 0 end ) as Not_In_Retry
   FROM 
      yesnotmp.msg_t msg_t
         JOIN yesnotmp.msg msg
            ON msg_t.msg_id = msg.id
            LEFT JOIN `retry` rty
               ON  msg_t.phone = rty.phone
              AND msg_t.sushi_sub_id = rty.sushi_subscription_id
   WHERE 
          msg_t.status = 'Failure.Provider.Connection'
      AND msg_t.send_time BETWEEN '2013-06-02' AND '2013-06-03' 
   GROUP BY
      msg_t.phone, 
      msg_t.sushi_sub_id

編集 -

電話、sushi_sub_id 参照の alias.field を明確にするために編集試行ごとに調整されました...フィールドの適切なテーブルを知っているので、msg_t テーブルにクエリの 4 つの部分すべてにインデックスがあることを確認します。

(ステータス、send_time、電話、sushi_sub_id)

「MAX(CASE...)」は。これは、それぞれの列の再試行テーブルへの左結合で行われるため、レコード (1 つ以上) がある場合、「電話」は有効な値になります。そのようなレコードが存在しない場合は、NULL になります。

于 2013-06-03T12:34:04.980 に答える