Como extrapolar datas no SQL Server para calcular o diário conta?

0

Pergunta

Esta é a forma como os dados se parece. É uma longa mesa

enter image description here

Preciso calcular o número de pessoas empregadas por dia

enter image description here

Como escrever SQL Server lógica para obter este resultado? Eu treid para criar uma tabela de DATAS e, em seguida, aderir, mas isso causou um erro porque a tabela é muito grande. Preciso de uma lógica recursiva?

sql sql-server tsql
2021-11-23 19:56:48
4
0

Para futuras perguntas, não poste imagens de dados. Em vez disso, use um serviço como o dbfiddle. Eu vou de qualquer maneira de adicionar um esboço de uma resposta, com uma melhor preparados pergunta que você poderia ter obtido uma resposta completa. De qualquer forma, aqui vai:

-- extrema is the least and the greatest date in staff table
with extrema(mn, mx) as (
    select least(min(hired),min(retired)) as mn
         , greatest(max(hired),max(retired)) as mx
    from staff
), calendar (dt) as (
    -- we construct a calendar with every date between extreme values
    select mn from extrema
    union all
    select dateadd(day, 1, d)
    from calendar
    where dt < (select mx from extrema)
)
-- finally we can count the number of employed people for each such date
select dt, count(1) 
from calendar c 
join staff s
    on c.dt between s.hired and s.retired
group by dt; 

Se você encontrar-se a fazer este tipo de cálculo, muitas vezes, é uma boa idéia para criar uma tabela de calendário. Você pode adicionar outros atributos, tais como se é de um dia no meio da semana, etc.

Com uma restrição:

CHECK(hired <= retired)

a primeira parte pode ser simplificada para:

with extrema(mn, mx) as (
    select min(hired) as mn
         , max(retired) as mx
    from staff
),
2021-11-23 20:45:14
0

Supondo que os Empregados Atuais têm um valor NULO data da aposentadoria

Declare @Date1 date = '2015-01-01'
Declare @Date2 date = getdate()

Select A.Date
      ,HeadCount = count(B.name)
 From ( Select Top (DateDiff(DAY,@Date1,@Date2)+1) 
               Date=DateAdd(DAY,-1+Row_Number() Over (Order By (Select Null)),@Date1) 
         From  master..spt_values n1,master..spt_values n2
      ) A
 Left Join YourTable B on A.Date >= B.Hired and A.Date <= coalesce(B.Retired,getdate())
 Group BY A.Date
2021-11-23 20:34:49
0

Você precisa de um calendário de mesa para isso. Você começa com o calendário, e a ESQUERDA se JUNTAR tudo o mais, usando BETWEEN lógica.

Você pode usar uma tabela real. Ou você pode gerar-na mosca, como este:

WITH
    L0 AS ( SELECT c = 1
            FROM (VALUES(1),(1),(1),(1),(1),(1),(1),(1),
                        (1),(1),(1),(1),(1),(1),(1),(1)) AS D(c) ),
    L1 AS ( SELECT c = 1 FROM L0 A, L0 B, L0 C, L0 D ),
    Nums AS ( SELECT rownum = ROW_NUMBER() OVER(ORDER BY (SELECT 1))
              FROM L1 ),
    Dates AS (
      SELECT TOP (DATEDIFF(day, '20141231', GETDATE()))
        Date = DATEADD(day, rownum, '20141231')
      FROM Nums
    )

SELECT
  d.Date,
  NumEmployed = COUNT(*)
FROM Dates d
JOIN YourTable t ON d.Date BETWEEN t.Hired AND t.Retired
GROUP BY
  d.Date;

Se as suas datas têm um componente de hora, então você precisa usar >= AND < lógica

2021-11-23 20:49:37
0

Tente limitar o âmbito de sua data de tabela. Neste exemplo, eu tenho uma tabela de datas chamado TallyStickDT.

SELECT dt, COUNT(name)
FROM (
    SELECT dt
    FROM tallystickdt
    WHERE dt >= (SELECT MIN(hired) FROM #employees)
    AND dt <= GETDATE()
) A
LEFT OUTER JOIN #employees E ON A.dt >= E.Hired AND A.dt <= e.retired
GROUP BY dt
ORDER BY dt
2021-11-23 20:44:03

Em outros idiomas

Esta página está em outros idiomas

Русский
..................................................................................................................
Italiano
..................................................................................................................
Polski
..................................................................................................................
Română
..................................................................................................................
한국어
..................................................................................................................
हिन्दी
..................................................................................................................
Français
..................................................................................................................
Türk
..................................................................................................................
Česk
..................................................................................................................
ไทย
..................................................................................................................
中文
..................................................................................................................
Español
..................................................................................................................
Slovenský
..................................................................................................................