descendente - order by sql ejemplos
MySQL obtiene la posiciĆ³n de fila en ORDER BY (6)
Con la siguiente tabla de MySQL:
+-----------------------------+
+ id INT UNSIGNED +
+ name VARCHAR(100) +
+-----------------------------+
¿Cómo puedo seleccionar una sola fila Y su posición entre las otras filas en la tabla, cuando se ordena por name ASC
. Entonces, si los datos de la tabla son así, cuando se ordenan por nombre:
+-----------------------------+
+ id | name +
+-----------------------------+
+ 5 | Alpha +
+ 7 | Beta +
+ 3 | Delta +
+ ..... +
+ 1 | Zed +
+-----------------------------+
¿Cómo podría seleccionar la fila Beta
obtener la posición actual de esa fila? El conjunto de resultados que estoy buscando sería algo como esto:
+-----------------------------+
+ id | position | name +
+-----------------------------+
+ 7 | 2 | Beta +
+-----------------------------+
Puedo hacer un simple SELECT * FROM tbl ORDER BY name ASC
luego enumerar las filas en PHP, pero parece un desperdicio cargar un conjunto de resultados potencialmente grande solo para una sola fila.
Esta es la única forma en que puedo pensar:
SELECT `id`,
(SELECT COUNT(*) FROM `table` WHERE `name` <= ''Beta'') AS `position`,
`name`
FROM `table`
WHERE `name` = ''Beta''
La posición de una fila en la tabla representa cuántas filas son "mejores" que la fila específica.
Entonces, debes contar esas filas.
SELECT COUNT (*) + 1 FROM table
WHERE name
<''Beta''
En caso de empate, se devuelve la posición más alta.
Si agrega otra fila con el mismo nombre de "Beta" después de la fila "Beta" existente, la posición devuelta seguirá siendo 2, ya que compartirían el mismo lugar en la clasificación.
Espero que esto ayude a las personas que buscarán algo similar en el futuro, ya que creo que el propietario de la pregunta ya resolvió su problema.
Si la consulta es simple y el tamaño del conjunto de resultados devuelto es potencialmente grande, puede intentar dividirlo en dos consultas.
La primera consulta con un criterio de filtrado estrecho solo para recuperar datos de esa fila, y la segunda consulta usa COUNT
con la cláusula WHERE
para calcular la posición.
Por ejemplo en tu caso
Consulta 1:
SELECT * FROM tbl WHERE name = ''Beta''
Consulta 2:
SELECT COUNT(1) FROM tbl WHERE name >= ''Beta''
Usamos este enfoque en una tabla con registro de 2M y esta es mucho más escalable que el enfoque de Ponies de OMG.
Tengo un problema muy similar, por eso no haré la misma pregunta, pero compartiré aquí lo que hice, también tuve que usar un grupo y ordené por AVG. Hay estudiantes, con firmas y calificaciones, y tuve que clasificarlos (en otras palabras, calculo primero la AVG, luego los pido en DESC, y finalmente tuve que agregar la posición (rango para mí), así lo hice Algo muy similar a la mejor respuesta aquí, con algunos pequeños cambios que se ajustan a mi problema):
Puse finalmente la columna de position
(rango para mí) en SELECT externo
SET @rank=0;
SELECT @rank := @rank + 1 AS ranking, t.avg, t.name
FROM(SELECT avg(students_signatures.score) as avg, students.name as name
FROM alumnos_materia
JOIN (SELECT @rownum := 0) r
left JOIN students ON students.id=students_signatures.id_student
GROUP BY students.name order by avg DESC) t
Utilizar esta:
SELECT x.id,
x.position,
x.name
FROM (SELECT t.id,
t.name,
@rownum := @rownum + 1 AS position
FROM TABLE t
JOIN (SELECT @rownum := 0) r
ORDER BY t.name) x
WHERE x.name = ''Beta''
... para obtener un valor de posición único. Esta:
SELECT t.id,
(SELECT COUNT(*)
FROM TABLE x
WHERE x.name <= t.name) AS position
t.name
FROM TABLE t
WHERE t.name = ''Beta''
... le dará a los lazos el mismo valor. IE: si hay dos valores en el segundo lugar, ambos tendrán una posición de 2 cuando la primera consulta dará una posición de 2 a uno, y 3 a la otra ...
puede ser lo que necesitas es agregar sintaxis
LÍMITE
entonces usa
SELECT * FROM tbl ORDER BY name ASC LIMIT 1
si solo necesitas una fila ...