2013-06-19 11 views
14

MySQL以外のものではかなり簡単です。IF条件実行クエリの実行、その他のクエリの実行

基本的には、私が使用しているインデックスのタイプと、特定の用語が返す結果の数に基づいて、いくつかの条件を切り替える必要があります。効果に

何か:

IF (SELECT COUNT(*) FROM table WHERE term LIKE "term") > 4000 
    EXECUTE QUERY A 
ELSE 
    EXECUTE QUERY B 

これはMySQLの文では可能ですか?

EDIT:

クエリA:

SELECT id 
FROM table_a 
FORCE INDEX(id) 
JOIN table_b ON table_a.id = table_b.id 
WHERE term LIKE "term" 
ORDER BY date 
LIMIT 100; 

クエリB:

SELECT id 
FROM table_a 
FORCE INDEX(term) 
JOIN table_b ON table_a.id = table_b.id 
WHERE term LIKE "term" 
GROUP BY term # These lines would be included for a few conditions not mentioned above.. but are necessary 
HAVING COUNT = 1 # same... 
ORDER BY date 
LIMIT 100; 

クエリスイッチの理由は、私が劇的に基づいて異なる結果時間を取得することです「用語」の人気。

+2

特に、「QUERY A」と「QUERY B」とは何ですか? SQLは、通常、この状況をクリエイティブなWHERE句で処理できるようにしますが、A&Bが十分に関連しているかどうかわからない限りは、言い表すことはできません。 –

+1

...そうでなければ、MySQLは、通常のクエリではなく、関数、トリガ、およびストアドプロシージャでフロー制御ロジックの使用を許可します。 –

+0

理論上 - はい( 'CASE'ステートメントと結合の助けを借りて)、両方のクエリのフィールドとレコードの数が一致するかどうかによって異なります。これらの2つをテストデータとともに投稿して、答えることができます。 –

答えて

16

EDIT:私は、ストアドプロシージャを必要とするについて、以下の言ったことは真実ではありません。これを試してみてください:

SELECT CASE WHEN ((SELECT COUNT(*) FROM table WHERE term LIKE "term") > 4000) 
    THEN <QUERY A> 
    ELSE <QUERY B> 
END 

これは、実際に、ケースの表現であり、それは例えば

:-)ストアドプロシージャ外で正常に動作します:歴史のために、以下の

mysql> SELECT CASE WHEN (5 > 4) THEN (SELECT 'foo') ELSE (SELECT 'bar') END; 
+---------------------------------------------------------------------+ 
| CASE WHEN (5 > 4) THEN (SELECT 'foo') ELSE (SELECT 'bar') END | 
+---------------------------------------------------------------------+ 
| foo                 | 
+---------------------------------------------------------------------+ 
1 row in set (0.01 sec) 

mysql> SELECT CASE WHEN (3 > 4) THEN (SELECT 'foo') ELSE (SELECT 'bar') END; 
+---------------------------------------------------------------------+ 
| CASE WHEN (3 > 4) THEN (SELECT 'foo') ELSE (SELECT 'bar') END | 
+---------------------------------------------------------------------+ 
| bar                 | 
+---------------------------------------------------------------------+ 
1 row in set (0.00 sec) 

古い答えをそれはすでにupvotesを集めているので、興味がある:

あなたが使用することができますが、ストアドプロシージャの内部:

CASE (SELECT COUNT(*) FROM table WHERE term LIKE "term") > 4000 
    WHEN 1 THEN <QUERY A> 
    ELSE <QUERY B> 
END CASE 

これはhttps://dev.mysql.com/doc/refman/5.0/en/case.htmlは、より多くの血みどろの詳細を持っている... CASE表現とは異なりCASE文です。

実際には、条件付きで別のクエリを実行したいのであれば、ストアドプロシージャを調べる必要があります。間違っている可能性があります。あなたがそれを行うことができれば、それはおそらくCASE式であるでしょう!

最後の編集:実際の例では、アプリケーション内で条件付きビットを実行し、SQL(またはSQLを生成するORM)に手渡すだけです検索する。

+1

これは、クエリが1行しか返さない場合にのみ機能します。そうしないと、サブクエリが1行以上を返すというエラーが発生します。 – fancyPants

4

試してみてください。

select coalesce(i.id, t.id) id 
from (SELECT COUNT(*) countterm FROM table WHERE term LIKE "term") c 
left join 
    (SELECT id, date 
     FROM table_a 
     FORCE INDEX(id) 
     JOIN table_b ON table_a.id = table_b.id 
     WHERE term LIKE "term") i on countterm > 4000 
left join 
    (SELECT id, date 
     FROM table_a 
     FORCE INDEX(term) 
     JOIN table_b ON table_a.id = table_b.id 
     WHERE term LIKE "term" 
     GROUP BY term 
     HAVING COUNT = 1) t on countterm <= 4000 
ORDER BY coalesce(i.date, t.date) 
LIMIT 100; 
+2

私はこれが正しい出力を提供する点でこれが好きですが、両方のクエリを実行するので、OPはそれを避けたいと確信しています。 – Bohemian

+0

@Bohemian: 'join ... on'(メインクエリに対して)条件がfalseの場合、実際にサブクエリを実行しますか? –

+1

私はこう考えています。なぜなら、ON条件は、結合された行の句(フィルター)と条件の偽りを最適化できないためです(事前に偽であることを知る方法はありません)。私は間違っている可能性があります... – Bohemian