Mysql order by union не работает
Вот мой запрос
(SELECT * FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%only three doors%" OR `joke` LIKE "%only three doors%") ORDER BY `ups` DESC,`downs` ASC)
UNION
(SELECT * FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%only%" OR `joke` LIKE "%only%") ORDER BY `ups` DESC,`downs` ASC)
UNION
(SELECT * FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%three%" OR `joke` LIKE "%three%") ORDER BY `ups` DESC,`downs` ASC)
UNION
(SELECT * FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%doors%" OR `joke` LIKE "%doors%") ORDER BY `ups` DESC,`downs` ASC)
LIMIT 0, 30
По какой-то причине он, похоже, не упорядочивается с помощью ups или downs... он просто бросает результаты назад в том порядке, в котором они, естественно, находятся в базе данных.
Когда я сокращаю его только на один запрос, он работает нормально, но кроме этого он, кажется, игнорирует его.
Я также не хочу делать заказ по всем результатам, иначе я бы поставил LIMIT 0,30 Order By blah
Ответы
Ответ 1
Из MySQL документация:
... использование ORDER BY для отдельных операторов SELECT подразумевает ничего о порядке, в котором строки появляются в конечном результате потому что UNION по умолчанию создает неупорядоченный набор строк.
В принципе единственный раз, когда ORDER
в объединении будет полезен, если вы используете LIMIT
.
Итак, если вы запросили следующее:
(SELECT * FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%only three doors%" OR `joke` LIKE "%only three doors%") ORDER BY `ups` DESC,`downs` ASC LIMIT 10)
UNION ...
Затем вы увидите первые десять записей, которые будут возвращены на основе этого заказа, но они не обязательно будут отображаться в порядке.
UPDATE:
Попробуйте это -
(SELECT *, 1 as ob FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%only three doors%" OR `joke` LIKE "%only three doors%") )
UNION
(SELECT *, 2 as ob FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%only%" OR `joke` LIKE "%only%") )
UNION
(SELECT *, 3 as ob FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%three%" OR `joke` LIKE "%three%") )
UNION
(SELECT *, 4 as ob FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%doors%" OR `joke` LIKE "%doors%"))
ORDER BY `ob`, `ups` DESC,`downs` ASC LIMIT 0, 30
Ответ 2
Я получил решение для этого:
SELECT *
FROM (
(SELECT 1 as SortRank, uid, title, state, zip, region,cantone FROM company WHERE city=".$city." AND region=".$region." AND cantone=".$cantone.")
UNION
(SELECT 2 as SortRank, uid, title, state, zip, region,cantone FROM company WHERE region=".$region." AND cantone=".$cantone.")
union all
(SELECT 3 as SortRank, uid, title, state, zip, region,cantone FROM company WHERE cantone=".$cantone.")
) As u
GROUP BY uid
ORDER BY SortRank,state=2, title ASC
LIMIT 0,10
В вышеприведенном запросе я хочу получить результат, например. сначала покажите все рекорды с городом, регионом и кантоном, а затем, если город недоступен, покажите все записи с регионом и кантоном, а затем все записи с кантоном города.
Таким образом, удаляя повторяющиеся записи, я использовал предложение GROUP BY, он будет сортировать все записи на основе группы запросов, а затем все записи с состоянием = 2.
Ответ 3
Что делает запрос, это упорядочить каждый дополнительный запрос отдельно и объединить все из них. Нет гарантии, что результат будет заказан.
то, что вам нужно сделать, - упорядочить единый запрос как таковой:
Select * from (
(SELECT *, 1 as `p` FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%only three doors%" OR `joke` LIKE "%only three doors%"))
UNION
(SELECT *, 2 as `p` FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%only%" OR `joke` LIKE "%only%"))
UNION
(SELECT *, 3 as `p` FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%three%" OR `joke` LIKE "%three%"))
UNION
(SELECT *, 4 as `p` FROM `jokes` WHERE `flags` < 5 AND (`title` LIKE "%doors%" OR `joke` LIKE "%doors%"))
) ORDER BY `p` ASC, `ups` DESC,`downs` ASC
Ответ 4
Вы должны иметь возможность использовать UNION ALL для удаления дубликатов (а также для полной сортировки набора результатов). Используя это, набор результатов должен быть порядка операторов select в запросе.