Сортировка запроса MySQL с несколькими объединенными таблицами

#mysql #sql

#mysql #sql

Вопрос:

Мой запрос использует левое соединение для извлечения нескольких значений из таблицы objects_values . У меня возникли проблемы с сортировкой результатов так, как я хочу; если ASC, сначала покажите объекты с наименьшими значениями атрибутов, а если DESC, сначала покажите объекты с наибольшими значениями атрибутов.

На самом деле мне удалось заставить его работать, когда направление заказа равно DESC, но когда направление равно ASC, результаты просто переходят к нижней части результатов, независимо от AttributeID.

Запрос, который помещает 237 результатов внизу, выглядит следующим образом:

 SELECT
    objects.id,
    objects.title,
    values.value
FROM objects
LEFT JOIN objects_values AS values ON values.objectId=objects.id
WHERE objects.categoryId IN (195)
ORDER BY
    CASE WHEN values.attributeId=237 THEN values.value END ASC,
    objects.id asc
  

Я хочу, чтобы запрос ВСЕГДА СНАЧАЛА упорядочивался по атрибуту 237 и помещал эти результаты первыми в результатах, независимо от того, равно ли значение 237 0,1 или 10.

Это было бы легко, если бы все объединенные таблицы имели уникальные имена, но этот запрос может содержать 20 различных атрибутов из таблицы objects_values .

Я неправильно подхожу к этому?

Ответ №1:

Для 237 начала вы можете использовать:

 ORDER BY (values.attributeId = 237) DESC
         objects.id asc
  

При этом используется функция MySQL, заключающаяся в том, что логические выражения обрабатываются как числа в числовом контексте, с «1» для true и «0» для false (вот почему DESC это необходимо для того, чтобы это было первым).

Это эквивалентно:

 ORDER BY (CASE WHEN values.attributeId = 237 THEN 1 ELSE 0 END) DESC
         objects.id asc
  

Комментарии:

1. Это такое простое решение, но я не мог разобраться сам 🙂 Спасибо!

Ответ №2:

Используйте case выражение, чтобы поставить 237 первым:

 ORDER BY CASE WHEN values.attributeId = 237 THEN 0 ELSE 1 END asc,
         values.value asc, objects.id asc
  

Совместимый с ANSI SQL, т.е. переносимый!