Hola de nuevo gerardo_goh:
Lamentablemente MySQL no cuenta con funciones RANK o ROW_COUNT que poseen otros motores como ORACLE o SQL Server, y que son las indicadas para hacer lo que necesitas, sin embargo hay varias técnicas que puedes utilizar para simular estas funciones. Checa esta liga:
RANK:
http://www.artfulsoftware.com/infotr...tip.php?id=460
ROW_NUMBER:
http://www.artfulsoftware.com/infotr...ip.php?id=1098
Como podrás observar la consulta no es tan trivial, pero en realidad no es tan complicada llevarla a la práctica. Me voy a enfocar sólo en lo que te falta que es el RANK de ventas... sería más o menos así, basándonos en los siguientes datos:
Código MySQL:
Ver originalmysql
> SELECT id_trab
, nombre
, zona
, ventas
FROM tblrango
;+---------+-----------+------+--------+
| id_trab | nombre | zona | ventas |
+---------+-----------+------+--------+
| 00013 | armando | 0015 | 25 |
| 00156 | ricardo | 0015 | 30 |
| 04566 | gerardo | 0015 | 20 |
| 01756 | francisco | 0120 | 30 |
| 02546 | jose | 0120 | 48 |
| 05630 | julian | 3000 | 40 |
| 09000 | pablo | 3000 | 30 |
| 12222 | ulises | 3000 | 31 |
| 12300 | jonathan | 3000 | 30 |
| 15460 | pedro | 3000 | 41 |
+---------+-----------+------+--------+
10 rows
in set (0.00 sec
)
La idea de la función RANK es hacer una subconsulta para cada registro donde cuentes cuantos registros existen con ventas mayores o iguales a la que se está analizando. Sería más o menos así:
Código MySQL:
Ver originalmysql
> SELECT v1.id_trab
, v1.nombre
, v1.zona
, -> v1.ventas
, COUNT(v2.ventas
) AS Rank
-> v1.ventas
< v2.ventas
OR -> (v1.ventas
= v2.ventas
AND v1.zona
= v2.zona
AND -> v1.id_trab = v2.id_trab)
-> GROUP BY v1.id_trab
, v1.zona
, v1.ventas
+---------+-----------+------+--------+------+
| id_trab | nombre | zona | ventas | Rank |
+---------+-----------+------+--------+------+
| 00156 | ricardo | 0015 | 30 | 1 |
| 00013 | armando | 0015 | 25 | 2 |
| 04566 | gerardo | 0015 | 20 | 3 |
| 02546 | jose | 0120 | 48 | 1 |
| 01756 | francisco | 0120 | 30 | 2 |
| 15460 | pedro | 3000 | 41 | 1 |
| 05630 | julian | 3000 | 40 | 2 |
| 12222 | ulises | 3000 | 31 | 3 |
| 09000 | pablo | 3000 | 30 | 4 |
| 12300 | jonathan | 3000 | 30 | 4 |
+---------+-----------+------+--------+------+
10 rows
in set (0.00 sec
)
También podrías hacerlo con la función ROW_NUMBER, la idea aquí es en primer lugar ordenar los registros por zona y por ventas, utilizar una variable temporal para almacenar la zona y un contador para la posición. Mientras se analice la misma zona, se va incrementando el contador para poner la posición, cuando se detecta un cambio de zona entonces se inicializa el contador a 1... sería más o menos así:
Primero inicializamos las variables temprales que vamos a utilizar:
Código MySQL:
Ver originalmysql
> SET @zonaPrev
=0, @ventasPrev
=0, @ordPrev
=0;Query OK, 0 rows affected (0.00 sec)
mysql
> SELECT id_trab
, nombre
, zona
, ventas
, row_number
-> ventas, id_trab, nombre,
-> @ordPrev
:= IF(@zonaPrev
= zona
, -> IF(ventas
!= @ventasPrev
, @ordPrev
+1, @ordPrev
), -> @zonaPrev
:= zona
AS zona
, -> @ventasPrev
:= ventas
AS ventasPrev
-> ) tmp;
+---------+-----------+------+--------+------------+
| id_trab | nombre | zona | ventas | row_number |
+---------+-----------+------+--------+------------+
| 00156 | ricardo | 0015 | 30 | 1 |
| 00013 | armando | 0015 | 25 | 2 |
| 04566 | gerardo | 0015 | 20 | 3 |
| 02546 | jose | 0120 | 48 | 1 |
| 01756 | francisco | 0120 | 30 | 2 |
| 15460 | pedro | 3000 | 41 | 1 |
| 05630 | julian | 3000 | 40 | 2 |
| 12222 | ulises | 3000 | 31 | 3 |
| 09000 | pablo | 3000 | 30 | 4 |
| 12300 | jonathan | 3000 | 30 | 4 |
+---------+-----------+------+--------+------------+
10 rows
in set (0.00 sec
)
Si comparas este ejercicio con el que te pongo en la liga, observarás que yo utilizo una segunda variable ventasTemp, esto es para evitar que cuando se trate de ventas iguales te ponga un orden distinto, como en los últimos dos registros, si lo hago como aparece en el ejemplo sería así:
Código MySQL:
Ver originalmysql
> SET @zonaPrev
=0, @ordPrev
=0;Query OK, 0 rows affected (0.00 sec)
mysql
> SELECT id_trab
, nombre
, zona
, ventas
, row_number
-> ventas, id_trab, nombre,
-> @ordPrev
:= IF(@zonaPrev
= zona
, @ordPrev
+1, 1) AS row_number
, -> @zonaPrev
:= zona
AS zona
-> ) tmp;
+---------+-----------+------+--------+------------+
| id_trab | nombre | zona | ventas | row_number |
+---------+-----------+------+--------+------------+
| 00156 | ricardo | 0015 | 30 | 1 |
| 00013 | armando | 0015 | 25 | 2 |
| 04566 | gerardo | 0015 | 20 | 3 |
| 02546 | jose | 0120 | 48 | 1 |
| 01756 | francisco | 0120 | 30 | 2 |
| 15460 | pedro | 3000 | 41 | 1 |
| 05630 | julian | 3000 | 40 | 2 |
| 12222 | ulises | 3000 | 31 | 3 |
| 09000 | pablo | 3000 | 30 | 4 |
| 12300 | jonathan | 3000 | 30 | 5 |
+---------+-----------+------+--------+------------+
10 rows
in set (0.00 sec
)
Observa que en los últimos dos registros les asigna rangos diferentes (4, 5).
Trata de analizar las consultas pero sobre todo trata de entenderlas, practica algunas otras consultas, estoy seguro que este tipo de consultas te servirán en un futuro.
Saludos.