Pessoal, no último post relacionei funções para trabalhar com campos do tipo data, acabei recebendo um bom feedback e algumas perguntas sobre como relacionar todos os meses ou dias da semana por meio de query. Para responder estas perguntas, relacionei formas de gerar listas com os meses e dias da semana por meio de CTE.
Nestas duas primeiras queries, faço uso de um CTE recursivo básico, com as funções DATENAME e DATEADD e a instrução SET LANGUAGE para definir o idioma ‘Brasileiro’. Estas queries são bem mais simples e tornam mais fácil trazer novos campos.
Tips:
1: Os campos de data quando somados a tipos inteiros, adicionam o valor dos inteiros em dias.
2: A função DATEADD simplifica a adição de outros quantitativos como meses, horas e anos.
3: O inteiro ’0′ (zero) quando convertido para data se torna ’1900-01-01 00:00:00.000′, uma segunda-feira.
4: O inteiro ‘-1′ quando convertido para data se torna ’1899-12-31 00:00:00.000′, um domingo.
Gerando uma lista de meses:
SET LANGUAGE 'Brazilian'
;WITH Meses AS
(
SELECT 1 AS IdMes, DATENAME(MONTH, 0) AS NomeMes
UNION ALL
SELECT IdMes + 1, DATENAME(MONTH, DATEADD(MONTH, IdMes, 0))
FROM Meses
WHERE IdMes < 12
)
SELECT * FROM MesesGerando uma lista de dias da semana começando pelo domingo:
SET LANGUAGE 'Brazilian'
;WITH DiaSemana AS
(
SELECT 1 AS idDSe, DATENAME(WEEKDAY, -1) AS nomeDSe
UNION ALL
SELECT idDSe + 1, DATENAME(WEEKDAY, idDSe -1)
FROM DiaSemana
WHERE idDSe < 7
)
SELECT idDSe, nomeDSe FROM DiaSemanaOu pela Segunda-Feira:
SET LANGUAGE 'Brazilian'
;WITH DiaSemana AS
(
SELECT 1 AS idDSe, DATENAME(WEEKDAY, 0) AS nomeDSe
UNION ALL
SELECT idDSe + 1, DATENAME(WEEKDAY, idDSe)
FROM DiaSemana
WHERE idDSe < 7
)
SELECT idDSe, nomeDSe FROM DiaSemanaNas duas próximas queries, avanço um pouco a complexidade das CTEs, utilizando a view syslanguage e uma CTE de Split que modifiquei do site do Zavaschi. Elas realmente se diferenciam pelo campo utilizado da syslanguages facilitando alterações neste sentido.
Gerando uma lista dos meses:
DECLARE @Texto VARCHAR(8000),
@Delimitador CHAR
SET @Texto = (SELECT months FROM sys.syslanguages WHERE alias = 'Brazilian')
SET @Delimitador = ','
;WITH _SPLIT(ID, _INDEX, _LENGTH) AS
(
SELECT
1,
1,
CHARINDEX(@Delimitador, @Texto + @Delimitador)
UNION ALL
SELECT
ID + 1,
_LENGTH + 1,
CHARINDEX(@Delimitador, @Texto + @Delimitador, _LENGTH + 1)
FROM _SPLIT
WHERE CHARINDEX(@Delimitador, @Texto + @Delimitador, _LENGTH + 1) <> 0
)
, Meses (idMes, nomeMes) AS
(
SELECT
ID,
SUBSTRING(@Texto, _INDEX, _LENGTH - _INDEX)
FROM _SPLIT
)
SELECT idMes, nomeMes FROM MesesGerando uma lista de dias da semana:
DECLARE @Texto VARCHAR(8000),
@Delimitador CHAR
SET @Texto = (SELECT days FROM sys.syslanguages WHERE alias = 'Brazilian')
SET @Delimitador = ','
;WITH _SPLIT(ID, _INDEX, _LENGTH) AS
(
SELECT
1,
1,
CHARINDEX(@Delimitador, @Texto + @Delimitador)
UNION ALL
SELECT
ID + 1,
_LENGTH + 1,
CHARINDEX(@Delimitador, @Texto + @Delimitador, _LENGTH + 1)
FROM _SPLIT
WHERE CHARINDEX(@Delimitador, @Texto + @Delimitador, _LENGTH + 1) <> 0
)
, DiaSemana (idDSe, nomeDSe) AS
(
SELECT
ID,
SUBSTRING(@Texto, _INDEX, _LENGTH - _INDEX)
FROM _SPLIT
)
SELECT idDSe, nomeDSe FROM DiaSemanaEu espero que elas respondam as necessidades que venham a aparecer!
Não se esqueçam de comentar!