ok, więc następujące zapytanie można prawdopodobnie wykonać bez podzapytania, ale zamiast tego ze sprzężeniem. Ufam, że optymalizator zapytań to zrobi, ale nie byłbym zbyt pewny.
SELECT l.name as language,
(SELECT cl.name
FROM country_languages cl
WHERE cl.country_id=[the wanted country id]
ORDER BY cl.language_id=l.id DESC,
cl.language_id=1 DESC
LIMIT 1) as country_name
FROM languages l
W tej wersji language_id 1 jest używany jako preferowana rezerwa, prawdopodobnie możesz dodać więcej języków w podobny sposób. Korzystanie z FIND_IN_SET
zamiast tego działałoby również jako kryterium drugiego rzędu (FIND_IN_SET(cl.language_id,'1,2,3') DESC
lub jakąkolwiek wolisz).
Oczywiście to zapytanie w tej chwili dotyczy stałego identyfikatora kraju. Może zostać rozszerzony w podobny sposób dla wielu krajów z innym połączeniem:
SELECT l.name as language,
(SELECT cl.name
FROM country_languages cl
WHERE cl.country_id=c.id
ORDER BY cl.language_id=l.id DESC,
cl.language_id=1 DESC
LIMIT 1) as country_name
FROM countries c
JOIN languages l
alternatywą dla podzapytań byłoby dwukrotne dołączenie do country_languages i wybranie pierwszego, który nie jest pusty (co jest prawdopodobnie jednym z czystszych rozwiązań):
SELECT l.name as language,
COALESCE(first.name, second.name) as country_name
FROM countries c
JOIN languages l
LEFT JOIN country_languages first ON
(first.country_id=c.id AND first.language_id=l.id)
LEFT JOIN country_languages second ON
(second.country_id=c.id AND second.language_id=1)
Jeśli identyfikator języka 1 to Twój język zapasowy. Można to również rozszerzyć, aby zapewnić wiele języków awaryjnych ...