Cómo definir un ORDEN personalizado POR orden en MySQL


En MySQL cómo defino un orden de clasificación personalizado.

Para tratar de explicar lo que quiero considerar esta tabla:

ID  Language    Text
0   ENU         a
0   JPN         b
0   DAN         c       
1   ENU         d
1   JPN         e
1   DAN         f
2   etc...

Aquí quiero devolver todas las filas ordenadas por Idioma e ID ascendente para que Language = ENU esté primero, luego JPN y finalmente DAN.

El resultado debe ser: a, d,b,e,c, f, etc.

¿Es esto posible?

 100
Author: Zbynek, 2012-02-21

3 answers

MySQL tiene una práctica función llamada FIELD() lo cual es excelente para tareas como esta.

ORDER BY FIELD(Language,'ENU','JPN','DAN'), ID

Tenga en cuenta, sin embargo, que

  1. Hace que su SQL sea menos portátil, ya que otros DBMSs podrían no tener dicha función

  2. Cuando su lista de idiomas (u otros valores para ordenar) se hace mucho más larga, es mejor tener una tabla separada con columna de orden de clasificación para ellos, y unirla a sus consultas para ordenar.

 217
Author: Mchl,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-08-01 06:26:50

Si esos son los únicos tres valores, entonces puede usar una expresión CASE :

ORDER BY `ID`,
         CASE `Language`
         WHEN 'ENU' THEN 1
         WHEN 'JPN' THEN 2
         WHEN 'DAN' THEN 3
         END

(Si puede haber otros valores, entonces es posible que desee agregar alguna lógica adicional para mantener el orden consistente; por ejemplo, puede agregar ELSE 4 a esa expresión CASE, y luego ordenar por Language como tercer criterio de orden:

ORDER BY `ID`,
         CASE `Language`
         WHEN 'ENU' THEN 1
         WHEN 'JPN' THEN 2
         WHEN 'DAN' THEN 3
         ELSE 4
         END,
         `Language`
)
 38
Author: ruakh,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-02-07 23:12:28

Tiene un par de opciones de forma improvisada, la primera es cambiar el Idioma para que sea ENUM (suponiendo que esto sea posible, y solo espere unas pocas variaciones)

Si lo especifica como ENUM('ENU','JPN','DAN') entonces ORDER Language ASC ordenará en el orden que especifique.

El segundo involucrará un caso en alguna parte, es decir,

SELECT * FROM table
ORDER BY CASE Language
    WHEN 'ENU' THEN 3
    WHEN 'JPN' THEN 2
    WHEN 'DAN' THEN 1
    ELSE 0
END DESC, ID ASC

En cuanto al rendimiento, el método ENUM devolverá resultados más rápidos, pero será más complicado si necesita agregar más idiomas. Una tercera opción sería añadir una tabla de normalización para el Idiomas sin embargo que pueden ser excesivos en este caso.

 14
Author: Simon at mso.net,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-12-20 09:57:31