2010-11-24 14 views
8

最初の照会を注文し、最初に返された行を維持し、2番目の照会を注文することはできません。私の現在の問い合わせの例があるMYSQL UNION ORDERING

(つまり、ローミングサービスを行った場合):

SELECT 
    * 
FROM 
    Devices 
WHERE 
    Live = 'true' 
    AND Category = 'apple' 
ORDER BY 
    ListOrder 
UNION 
SELECT 
     * 
    FROM 
     Devices 
    WHERE 
     DeviceLive = 'true' 

私は、カテゴリリンゴの下のデバイスがリスト順に編成されることを期待していたとの上部にあるだろう他のデバイスの上に表示されます。しかし、これは2つのクエストを混乱させるようです。

答えて

15

人工的なソートキーを導入する必要があります。何かのように:

SELECT 
    *, 1 as SortKey 
FROM 
    Devices 
WHERE 
    Live = 'true' 
    AND Category = 'apple' 
UNION 
SELECT 
     *, 2 as SortKey 
    FROM 
     Devices 
    WHERE 
     DeviceLive = 'true' 
ORDER BY SortKey, ListOrder 
+0

これは私が過去にそれを達成した方法です – Sonny

+0

おかげでジョーのように働いた! – Yardstermister

+0

こんにちは、私は人工的なソートキーを作る必要はなかった、私はちょうど各テーブルは、私が並べ替えたい列の同じ名前を持っていたことを確認した。私の場合、列名は「注文」でした。だから私はしました:選択*、テーブルからの注文を選択します。UNION select *、テーブル2から注文します。オーダーBY uOrder –

2

あなたが偽の可能性、それ

SELECT col1, col2 ... 
FROM (
    SELECT 1 fake_order, col1, col2 ... FROM Devices WHERE Live ='true' AND Category='apple' ORDER BY ListOrder 
    UNION ALL 
    SELECT 2, col1, col2 ... FROM Devices WHERE DeviceLive ='true' 
) AS T 
ORDER BY fake_order 

(私の頭の上からテストされていないSQL)

+0

これは古いですが、完全であることを私は知っています。これを動作させるための内側のクエリに名前を付ける必要があります。 –

+0

@TomHeard - ありがとう、私はクエリを更新しました – Tony

+0

'AS'をドロップし、あなたはいいです。 –

2

UNIONは、暗黙の重複排除機能を持っています。これは、それを使用する副作用が起こることが分かれば、すべてが混乱することを意味します。また、通常は必ずしもそうではありませんが、ソートされた出力を得ることを意味します(次の段落を参照してください)。

UNION ALLはこれを削除しますが、明示的なorder byのないクエリからの出力には順序保証がありません。これは別の答えでカバーされていますが、なぜ重要なのかを指摘する価値があると思いました。

+0

ありがとう、私の実行計画がソートを行っていた理由を探していました。これはそれと私の奇妙な注文の問題に答える。 –

0

私はジョー・ステファネリから私の答えを得たが、少しはそれを修正:

こんにちは、私は私がちょうど各テーブルの両方が同じ名前を持っていたことを確認しました、人工的なソート・キーを作成する必要はありませんでした私は並べ替えたいと思っていました。私の場合、列名は「注文」でした。だから私はした:

Select *, order as uOrder from table 1 
UNION 
select *, order as uOrder from table 2 
ORDER BY uOrder