none
Obtener top 10, en un rango de x numero de registros RRS feed

  • Pergunta

  • Buen dia a todos, tengo 2 tablas, de las cuales al unirlas obtengo aproximadamente 80 registros de la siguiente manera:

    SELECT IdEmp, NameEmp, SUM(Tot) AS Total
    FROM HorasLaboradas
    INNER JOIN empleados ON empleados.NumEmp = HorasLaboradas.NumEmpl 
    GROUP BY IdEmp, NameEmp
    ORDER BY Total DESC

    Hasta aqui todo bien, obtengo todos los empleados con su nombre y un total de horas.

    Aqui es donde tengo la siguiente duda:

    Tengo un numero de empleado, y deseo obtener los 5 registros anteriores y los 5 registros posteriores del usuario que estoy buscando, es decir un top 10, pero apartir de un empleado, esto es para obtener una lista de 10 empleados, pero siempre debe aparecer el usuario que busco.

    Por ejemplo si buscara al empleado 500 pero apareceria en la posicion 25, tendria q obtener un top entre la posicion 10 y 30

    Posicion  NumeroEmpleado Total

     20          235                    65

     21          120                    60

     22          050                    58

     22          003                    55

     23          355                    50

     24          189                    45

     25          500                    40

     26          001                    35

     27          100                    30

     28          380                    27

     29          070                    25

     30          200                    20

    Pueden guiarme sobre si es posible realizar esto en una sentencia sql?, o pueden quiarme?, uso sql server 2012.


    sábado, 17 de agosto de 2019 19:02

Todas as Respostas

  • Podrías usar la cláusula OVER junto con "... ROWS BETWEEN 5 PRECEDING AND 5 FOLLOWING". Precisamente se introdujo por primera vez con la versión 2012 de SQL Server, que es justo la que tienes.

    https://docs.microsoft.com/en-us/sql/t-sql/queries/select-over-clause-transact-sql?view=sql-server-2017

    sábado, 17 de agosto de 2019 19:34
  • Muchas gracias, lo consutare.
    sábado, 17 de agosto de 2019 20:27
  • Tengo un numero de empleado, y deseo obtener los 5 registros anteriores y los 5 registros posteriores del usuario que estoy buscando,

    Pruebe

    -- código #1
    declare @Empleado int, @posicion int;
    set @Empleado= 500;
    
    --
    IF Object_ID('tempDB..#rank_empleado', 'U') is not null
      DROP TABLE #rank_empleado;
    
    --
    SELECT IdEmp, NameEmp, SUM(Tot) AS Total,
           posicion= row_number() over (partition by IdEmp 
    order by SUM(Tot) desc, NameEmp asc) INTO #rank_empleado FROM HorasLaboradas INNER JOIN empleados ON empleados.NumEmp = HorasLaboradas.NumEmpl GROUP BY IdEmp, NameEmp;
    CREATE unique clustered INDEX I1_rank on #rank_empleado (posicion);
    -- set @posicion= (SELECT top (1) posicion from #rank_empleado where IdEmp = @Empleado); SELECT posicion, IdEmp, NameEmp, Total from #rank_empleado where posicion between (@posicion -5) and (@posicion +5)
    order by posicion, NameEmp; -- IF Object_ID('tempDB..#rank_empleado', 'U') is not null DROP TABLE #rank_empleado;
     

    o

    -- código #2
    declare @Empleado int, @posicion int;
    set @Empleado= 500;
    
    --
    with Calculo as (
    SELECT IdEmp, NameEmp, SUM(Tot) AS Total,
           posicion= row_number() over (partition by IdEmp 
    order by SUM(Tot) desc, NameEmp asc) FROM HorasLaboradas INNER JOIN empleados ON empleados.NumEmp = HorasLaboradas.NumEmpl GROUP BY IdEmp, NameEmp ) SELECT top (11) posicion, IdEmp, NameEmp, Total from Calculo where posicion >= (SELECT posicion from Calculo where IdEmp = @Empleado) -5;
     

    Use el código # 2 solo para pequeños volúmenes de datos.

     

    Si esta respuesta te ayudó a resolver tu problema, recuerda marcarla.


    José Diz     Belo Horizonte, MG - Brasil     [T-SQL performance tuning: Porto SQL]   [e-mail]


    Este conteúdo é fornecido sem garantias de qualquer tipo, seja expressa ou implícita.

    • Editado José Diz domingo, 18 de agosto de 2019 16:35
    domingo, 18 de agosto de 2019 14:15