V SQL, ORDER BY
klauzule se běžně používá k uspořádání výsledků dotazu. Umožňuje vám vybrat jeden nebo více sloupců pro uspořádání výsledků a ve většině případů je to pravděpodobně vše, co potřebujete.
Ale co když potřebujete udělat výjimku?
Co když chcete, aby byly výsledky seřazeny podle abecedy, kromě jednoho řádku? Nebo několik řádků?
Nebo možná jednoduše chcete zapsat jakékoli hodnoty NULL na konec a přitom seřadit výsledky, které nejsou NULL.
Ať tak či onak, existuje úhledný trik, který můžete použít a který vám to umožní. A nejlepší na tom je, že je to jednoduché.
Všechny výše uvedené scénáře můžete pokrýt přidáním CASE
výraz do vašeho ORDER BY
doložka.
Příklad 1 – Přesunutí „Ostatní“ dolů
Předpokládejme, že spustíme následující dotaz proti tabulce obsahující hudební žánry.
SELECT Genre
FROM MusicGenres
ORDER BY Genre ASC;
Výsledek:
+---------+ | Genre | |---------| | Blues | | Country | | Hip Hop | | Jazz | | Metal | | Other | | Pop | | Rap | | Rock | +---------+
V tomto případě seřadíme výsledky podle Genre
sloupec, ve vzestupném pořadí.
To je fajn, až na jednu věc. Žánr s názvem Ostatní . Nebylo by hezké, kdybychom mohli přesunout Jiné na dno?
Toho můžeme dosáhnout pomocí CASE
výraz. Proto můžeme vzít výše uvedený dotaz a upravit jeho ORDER BY
doložka takto.
SELECT Genre
FROM MusicGenres
ORDER BY
CASE Genre
WHEN 'Other' THEN 1
ELSE 0
END
ASC, Genre ASC;
Výsledek:
+---------+ | Genre | |---------| | Blues | | Country | | Hip Hop | | Jazz | | Metal | | Pop | | Rap | | Rock | | Other | +---------+
Příklad 2 – Přesunutí hodnot NULL dolů
Pokud váš stůl náhodou obsahuje některou z těchto otravných hodnot NULL, zjistíte, že budou trvat na tom, aby zůstali nahoře, když budete objednávat ve vzestupném pořadí.
Ještě jednou CASE
výraz k záchraně!
Představme si, že výše uvedená tabulka obsahuje několik hodnot NULL. A když spustíme náš dotaz, vypadá to spíše takto:
SELECT Genre
FROM MusicGenres
ORDER BY
CASE Genre
WHEN 'Other' THEN 1
ELSE 0
END
ASC, Genre ASC;
Výsledek:
+---------+ | Genre | |---------| | NULL | | NULL | | Blues | | Hip Hop | | Jazz | | Metal | | Pop | | Rock | | Other | +---------+
Nyní tedy chceme posunout hodnoty NULL dolů – ještě níže než Jiné .
Můžeme to udělat pomocí následujícího dotazu.
SELECT Genre
FROM MusicGenres
ORDER BY
CASE
WHEN Genre IS NULL THEN 2
WHEN Genre = 'Other' THEN 1
ELSE 0
END
ASC, Genre ASC;
Výsledek:
+---------+ | Genre | |---------| | Blues | | Hip Hop | | Jazz | | Metal | | Pop | | Rock | | Other | | NULL | | NULL | +---------+
V tomto příkladu jsme použili jiný CASE
formát. V tomto příkladu jsme použili vyhledaný CASE
výraz , na rozdíl od předchozího příkladu, který používal jednoduchý CASE
výraz .
Hledaný CASE
expression vyhodnotí sadu booleovských výrazů k určení výsledku.
Jednoduchý CASE
výraz na druhé straně porovnává výraz se sadou jednoduchých výrazů a určuje výsledek.
Jednoduchý CASE
výraz má vstupní výraz vedle CASE
klíčové slovo, zatímco hledaný CASE
výraz ne.
Příklad 3 – Upravit některé řádky nahoru
Nyní si představte, že chceme mít jeden nebo více řádků, které jsou vždy na začátku výsledků, bez ohledu na to, kam se vejdou do pořadí širších výsledků.
Například:
SELECT * FROM vAlbums
ORDER BY ArtistName ASC, AlbumName ASC;
Výsledek:
+------------------------+--------------------------+---------+ | ArtistName | AlbumName | Genre | |------------------------+--------------------------+---------| | AC/DC | Powerage | Rock | | Allan Holdsworth | All Night Wrong | Jazz | | Allan Holdsworth | The Sixteen Men of Tain | Jazz | | Buddy Rich | Big Swing Face | Jazz | | Devin Townsend | Casualties of Cool | Rock | | Devin Townsend | Epicloud | Rock | | Devin Townsend | Ziltoid the Omniscient | Rock | | Iron Maiden | Killers | Rock | | Iron Maiden | No Prayer for the Dying | Rock | | Iron Maiden | Piece of Mind | Rock | | Iron Maiden | Powerslave | Rock | | Iron Maiden | Somewhere in Time | Rock | | Jim Reeves | Singing Down the Lane | Country | | Michael Learns to Rock | Blue Night | Pop | | Michael Learns to Rock | Eternity | Pop | | Michael Learns to Rock | Scandinavia | Pop | | The Script | No Sound Without Silence | Pop | | Tom Jones | Along Came Jones | Pop | | Tom Jones | Long Lost Suitcase | Pop | | Tom Jones | Praise and Blame | Pop | +------------------------+--------------------------+---------+
Tyto výsledky jsou seřazeny podle ArtistName
a poté pomocí AlbumName
.
Ale nahrávací společnost se rozhodla, že chtějí udělat speciální propagaci pro Toma Jonese . A tak chtějí Toma Jonese zobrazí se na začátku výsledků, ale všechny zbývající výsledky je třeba seřadit tak, jak jsou – abecedně podle jména interpreta a poté podle názvu alba.
V tomto případě můžeme provést následující:
SELECT * FROM vAlbums
ORDER BY
CASE ArtistName
WHEN 'Tom Jones' THEN 0
ELSE 1
END,
ArtistName ASC, AlbumName ASC;
Výsledek:
+------------------------+--------------------------+---------+ | ArtistName | AlbumName | Genre | |------------------------+--------------------------+---------| | Tom Jones | Along Came Jones | Pop | | Tom Jones | Long Lost Suitcase | Pop | | Tom Jones | Praise and Blame | Pop | | AC/DC | Powerage | Rock | | Allan Holdsworth | All Night Wrong | Jazz | | Allan Holdsworth | The Sixteen Men of Tain | Jazz | | Buddy Rich | Big Swing Face | Jazz | | Devin Townsend | Casualties of Cool | Rock | | Devin Townsend | Epicloud | Rock | | Devin Townsend | Ziltoid the Omniscient | Rock | | Iron Maiden | Killers | Rock | | Iron Maiden | No Prayer for the Dying | Rock | | Iron Maiden | Piece of Mind | Rock | | Iron Maiden | Powerslave | Rock | | Iron Maiden | Somewhere in Time | Rock | | Jim Reeves | Singing Down the Lane | Country | | Michael Learns to Rock | Blue Night | Pop | | Michael Learns to Rock | Eternity | Pop | | Michael Learns to Rock | Scandinavia | Pop | | The Script | No Sound Without Silence | Pop | +------------------------+--------------------------+---------+