Criando uma tabela calendário com SQL

Criando uma tabela calendário com SQL

Neste artigo vamos ver como podemos criar uma tabela calendário com SQL

Uma tabela calendário pode ser utilizada para controlar dias úteis e feriados. Nos exemplos apresentados neste artigo vamos ver como criar uma tabela calendário no SQL Server e no MySQL. Nossa tabela vai ter todas as datas de um determinado intervalo de tempo, com a marcação de qual é o dia da semana daquela data. bem como o número da semana daquela data e a qual trimestre ela pertence.

Vamos começar pelo SQL Server. Primeiro vamos criar a tabela que vai guardar as datas de nosso calendário:

 

CREATE TABLE Calendario(

[Data] [date] NULL,

[Dia] [int] NULL,

[Mes] [int] NULL,

[Ano] [int] NULL,

[DiaSemana] [int] NULL,

[NumeroSemana] [int] NULL,

[Trimestre] [int] NULL,

[DiaUtil] [bit] NULL

)

 

Agora vamos criar um script que será executado para preencher essa tabela com todas as data do período informado. Este script vai utilizar um laço de repetição chamado WHILE para incrementar a data e inserir novos registros nesta tabela. Ao mesmo tempo, vai separar algumas informações. Neste exemplo, vamos criar um calendário com as datas do ano de 2024.

 

SET DATEFORMAT ymd

DECLARE @Data_Inicial datetime

DECLARE @Data_Final datetime

DECLARE @Dia INT

DECLARE @Mes INT

DECLARE @Ano INT

DECLARE @DiaUtil BIT

DECLARE @DiaSemana INT

DECLARE @NumeroSemana INT

DECLARE @Trimestre INT

SET @Data_Inicial = '2023-12-31'

SET @Data_Final = '2024-12-31'

WHILE(@Data_Inicial < @Data_Final)

BEGIN

SELECT @Data_Inicial = DATEADD(day, 1,@Data_Inicial)

SELECT @DiaSemana = DatePart(dw,@Data_Inicial) 

SELECT @NumeroSemana = DatePart(ww,@Data_Inicial) 

SELECT @Trimestre = DatePart(qq,@Data_Inicial) 

SELECT @Dia = DAY( @Data_Inicial)

SELECT @Mes = MONTH ( @Data_Inicial)

SELECT @Ano = YEAR ( @Data_Inicial)

IF DATEPART(dw, @Data_Inicial) IN (1,7)

SELECT @DiaUtil = 0

ELSE

SELECT @DiaUtil = 1

INSERT INTO Calendario (Data, Dia, Mes, Ano, DiaUtil, DiaSemana, NumeroSemana, Trimestre)

SELECT @Data_Inicial, @Dia, @Mes, @Ano, @DiaUtil, @DiaSemana,  @NumeroSemana, @Trimestre

END

 

Durante a execução do laço de repetição WHILE utilizamos as funções DAY. MONTH e YEAR para extrar dia, mês e ano da data atual que estava sendo iterada. O incremento dentro do WHILE foi feito pela função DATEADD, que sempre acrescentou 1 dia a cada interação. Para saber se a data era um final de semana, utilizamos DATEPART, que retornou um número referente ao dia da semana. DATEPART também foi utilizado para retornar o número da semana e o número do trimestre. Em nosso calendário, os dias marcados com DiaUtil= 1 são datas de segunda a sexta, sabádos e domingos são marcados com 0.

 

Chegou a hora de ver como podemos implementar isso no MySQL. Vamos começar criando a tabela calendário:

 

CREATE TABLE Calendario(

Data date NULL,

Dia int NULL,

Mes int NULL,

Ano int NULL,

DiaSemana int NULL,

NumeroSemana int NULL,

Trimestre int NULL,

DiaUtil bit NULL

)

 

E agora vamos ver como criar o calendário usando o MYSQL. Vamos encapsultar a lógica que vai gerar o calendário dentro de uma procedure que vai receber dois parametros, a data inicial e a data final. Da mesma forma que fizemos no SQL Server, utilizaremos um laço de repetição WHILE, com algumas pequenas diferenças em relação ao exemplo anterior.

 

DELIMITER //

CREATE PROCEDURE periodoCalendario(data_inicial DATE, data_final DATE) 

BEGIN

DECLARE data_atual DATE;

    SET data_atual = data_inicial;

    WHILE data_atual <= data_final DO

        INSERT INTO Calendario VALUES (data_atual, DAY(data_atual), MONTH(data_atual), YEAR(data_atual), DAYOFWEEK(data_atual), WEEKOFYEAR(data_atual), QUARTER(data_atual),CASE DAYOFWEEK(data_atual) WHEN 1 THEN 0 WHEN 7 then 0 ELSE 1 END);

        SET data_atual = ADDDATE(data_atual,INTERVAL 1 DAY);

    END WHILE;

END //

DELIMITER ;

CALL periodoCalendario('2024-01-01', '2024-12-31');

 

Da mesma forma que foi feito no SQL Server, no MySQL temos as funções DAY, MONTH e YEAR para retornar dia, mês e ano de uma data. Para retornar o número da semana utilizamos WEEKOFYEAR e para retornar o número da semana utilizamos QUARTER. A função DAYOFWEEK retorna o número do dia da semana, com base nesse resultado retornamos se a data é um final de semana ou não.

EXEMPLOS DE UTIILZAÇÃO

Agora com a tabela calendário em mãos fica fácil controlar dias úteis. No exemplo a seguir vamos ver como listar os 45 dias úteis a partir de uma determinada data.

 

SQL Server

SELECT TOP 25 * FROM Calendario WHERE data >= '2024-02-04' AND DiaUtil = 1 ORDER BY Data;

 

MySQL

SELECT * FROM Calendario WHERE data >= '2024-02-04' AND DiaUtil = 1 ORDER BY Data LIMIT 45;

 

Para saber qual o primeiro dia útil de cada mês podemos fazer a seguinte consulta:

 

SELECT Mes, MIN(Data) as Data  FROM Calendario WHERE DiaUtil = 1 GROUP BY Mes ORDER BY Mes 

 

 

Outros conteudos que podem ser de seu interesse

SQL vs Excel - tabelas dinâmicas e agrupamento de resultados
16/01/2022SQL

SQL vs Excel - tabelas dinâmicas e agrupamento de resultados

Compare as formas de agrupar resultados no Excel e no SQL

Saiba mais...
SQL vs Mongo - expressões regulares
22/12/2019SQL

SQL vs Mongo - expressões regulares

Veja como utilizar expressões regulares no SQL e no Mongo

Saiba mais...

Conteúdo sobre banco de dados sem complicação!