SQL Server Datetime vs. Datetime2

existem muitos formatos de tempo e data no servidor SQL com diferentes intervalos, precisões, tamanhos de armazenamento e segunda precisões fraccionais definidas pelo utilizador.

abaixo está uma breve visão geral:

queremos focar na comparação do datetime e formato datetime2. Na minha empresa Actual encontro muitas tabelas de legado que usam datetime. Datetime2 foi introduzido pela primeira vez no servidor SQL 2008. No entanto, acho que alguns desenvolvedores simplesmente não sabem sobre as vantagens e desvantagens do datetime2.

Datetime

vamos primeiro discutir datetime um pouco. Como você pode ver acima, ele precisa de 8 bytes de armazenamento e tem um intervalo de 1753-01-01 a 9999-12-31. Notavelmente, tem um curto alcance para trás. Isso porque a Grã-Bretanha mudou-se do Calendário juliano para o gregoriano em 1752, faltando alguns dias. Para ser mais preciso, o 2 de setembro de 1752 foi seguido por 14 de setembro de 1752. Como uma data antes de 1753 seria ambígua, o tipo datetime não é válido antes de 1753. Outra propriedade bastante notável do DateTime datatype é a precisão de 0,00333 segundos que é de fato 1/300 de um segundo.Isto parece um pouco estranho. Não temos precisão de milissegundos com datetime. Está bem, mas porquê? Vamos analisar o DateTime datatype em profundidade. Em um datetime usamos 4 bytes para a data e 4 bytes para o tempo. Como é que isso funciona exactamente? Vamos ver.

DECLARE @test DATETIME = '2015-11-29 10:00:00.000';SELECT CAST(@test as varbinary(8))> 0x0000A55F00A4CB80

So 0x0000A55F00A4CB80 is hexadecimal. Separemos os 8 bytes em dois pedaços. Primeiro o encontro. 0x0000A55F representa a data. Em decimal é 42335. Essa é a quantidade de dias passados desde 1900-01-01. Prova:

SELECT DATEADD(DD,42335,'1900-01-01')> 2015-11-29

agora para o tempo nós temos os últimos 4 bytes 0xA4CB80 traduzidos para decimal é 10800000. Isso significa 10800000 carrapatos a partir da meia-noite. Lembras-te que disse que a precisão é de 1/300 de segundo? Isso é devido ao fato de que datetime armazena o tempo em carrapatos. Então 10800000 carraças desde a meia-noite significa 10800000 vezes 1/300 de segundo. Vamos calcular um pouco.

temos exactamente 10 horas da meia-noite e isso traduz-se perfeitamente às 10:00. Combinado com a data de 2015-11-29 10:00.

lembre-se que o datetime usa sempre 8 bytes de armazenamento e também tenha em mente que os primeiros quatro bytes representando a data pode ser negativo (2complement) uma vez que a data pode ser antes de 1900. Por exemplo, em 1890-11-29 você recebe os primeiros 4 bytes como 0xFFFFF308, que se traduz como 32-bit 2-complemento para -3320. E 3320 substracted from 1900-01-01 is exactly 1890-11-29.

datetime2

todos os tipos de dados de data e hora introduzidos com o servidor SQL 2008 têm um tipo de armazenamento completamente novo que vamos examinar agora. O datetime2 datatype usa 6 a 8 bytes dependendo da precisão do milisegundo.

DECLARE @test DATETIME2(3) = '2015-11-29 10:00:00.000';SELECT CAST(@test as varbinary(8))> 0x0300512502BA3A0B

desta vez fica um pouco mais complicado. Em todos os novos tipos de dados datetime, os últimos três bytes representam a data. Isso é devido a uma mudança de ordem de byte. Então datetime é armazenado como pequeno endian, o que significa que o byte mais significativo está no mais à esquerda, enquanto no big endian o byte mais significativo é armazenado na posição mais à direita.

isso significa Que, quando tomamos 0x0300512502BA3A0B a data não é 0xBA3A0B mas 0x0B3ABA, uma vez que um byte é de 2 dígitos hexadecimais.

Novamente com a matemática: 0x0B3ABA representa o decimal 735930. Esta é exactamente a data que queríamos.:

SELECT DATEADD(DD,735930,CAST('0001-01-01' as date))> 2015-11-29

agora que os bytes são convertidos podemos apenas tomar os últimos bytes de pequena representação endiana que é 0x0225510003. Tenha em mente que o último byte em little endian (que é o primeiro byte no original big endian) é a precisão indicada. Como podem ver, definimos datetime2 (3) que significa que o nosso último byte é 0x03.

fazendo as contas: 0x02255100 é na casa decimal 36000000. Uma vez que usamos precisão 3, que significa precisão de 3 dígitos, calculamos os segundos primeiro dividindo o nosso número com 10 ao poder de precisão que é no nosso caso 103.

isto também se traduz perfeitamente para 10 horas 0 minutos 0 segundos, tal como indicado.

datetime vs datetime2

finalmente uma comparação simples e simples entre estes dois tipos de dados.

datetime datetime2
max precisa ímpar precisão de 1/300 precisão de 100 nanossegundos
definido pelo usuário precisão não sim variando de 0 a 7
espaço de armazenamento sempre 8 bytes 6 – 8 bytes, dependendo da precisão
utilizável com + ou – operador sim não, usar o datediff, dateadd etc.
SQL Padrão compatível não sim

Portanto, em geral, você vê datetime usa potencialmente mais espaço de armazenamento, tem um menor e ímpar de precisão, tem menor alcance e não é compatível com o Padrão SQL, o que torna o seu código se comportam de maneira diferente em diferentes SGBDS. Por isso, se a sua aplicação suporta data, datetime2 e datetimeoffset, aconselho fortemente a usar os novos datatetime datatypes, uma vez que eles têm quase nenhuma desvantagem.Obrigado pelo seu tempo. Para artigos mais interessantes visite http://www.dirtyread.de/

Deixe uma resposta

O seu endereço de email não será publicado.