DateTime2 vs DateTime w SQL Server

762

Który:

jest zalecany sposób, aby data i czas przechowywania w SQL Server 2008+?

Zdaję sobie sprawę z różnic w precyzji (i prawdopodobnie przestrzeni dyskowej), ale na razie je ignorując, czy istnieje dokument z najlepszymi praktykami określający, kiedy użyć, a może powinniśmy używać datetime2tylko?

Mikeon
źródło

Odpowiedzi:

641

Dokumentacja MSDN dla datetime zaleca używanie datetime2 . Oto ich zalecenie:

Użyj time, date, datetime2i datetimeoffsettypy danych do nowej pracy. Te typy są zgodne ze standardem SQL. Są bardziej przenośne. time, datetime2I datetimeoffset zapewnić precyzję więcej sekund. datetimeoffsetzapewnia obsługę stref czasowych dla aplikacji wdrażanych globalnie.

datetime2 ma większy zakres dat, większą domyślną precyzję ułamkową i opcjonalną precyzję określoną przez użytkownika. Również w zależności od precyzji określonej przez użytkownika może zużywać mniej pamięci.

Adam Porad
źródło
46
podczas gdy zwiększa się precyzja w datetime2, niektórzy klienci nie obsługują daty, godziny ani datetime2 i zmuszają cię do konwersji na literał łańcuchowy. Jeśli bardziej
zależy Ci na kompatybilności
4
Inną opcją jest użycie widoku indeksowanego z kolumną przekonwertowaną na datę i godzinę w celu zachowania zgodności. Musisz jednak móc skierować aplikację na widok.
TamusJRoyce,
9
Obsługa stref czasowych za pomocą DATETIMEOFFSET jest myląca. Przechowuje tylko przesunięcie UTC dla określonej chwili, a nie strefę czasową.
Suncat2000
6
@Porad: Jaka jest konkretna korzyść w praktyce z bycia „bardziej przenośnym” dzięki temu, że jest „SQL Standard”? To znaczy poza tym, że piszesz znacznie więcej kodu, który jest znacznie mniej czytelny / możliwy do utrzymania dla „portu” do innego RDBMS, który najprawdopodobniej nigdy nie wystąpi przez cały czas istnienia tego kodu. Poza narzędziami i sterownikami SQL Server dostarczonymi przez Microsoft (jeśli nawet) istnieją aplikacje, które faktycznie polegają na określonych reprezentacjach bitowych DateTime2typu (lub dowolnego innego programu SQL Server Wpisz tę sprawę)? Zobacz wady w mojej odpowiedzi z 7/10/17 poniżej, dlaczego pytam
Tom
2
@Adam Porad: Ponadto wszystkie te korzyści są prawdopodobnie niepotrzebne (poza aplikacjami inżynieryjnymi lub naukowymi) i dlatego nie są warte utraty wielu korzyści, DUŻO bardziej potrzebne: znacznie łatwiejsza (nawet biorąc pod uwagę obejścia) możliwość niejawnej / jawnej konwersji na zmiennoprzecinkowa wartość liczbowa (liczba dni włącznie, jeśli dotyczy, dni ułamkowe od min data-godzina) dla dodawania, odejmowania, minimów, maksimów i średnich. Zobacz minusy w mojej odpowiedzi z 7/10/17 poniżej, aby uzyskać szczegółowe informacje.
Tom
493

DATETIME2ma zakres dat od „ DATETIME0001/01/01 ” do „ 9999/12/31 ”, podczas gdy typ obsługuje tylko lata 1753-9999.

Ponadto, jeśli potrzebujesz, DATETIME2możesz być bardziej precyzyjny pod względem czasu; DATETIME jest ograniczony do 3 1/3 milisekund, a DATETIME2może być dokładny do 100ns.

Oba typy mapują na System.DateTime.NET - nie ma różnicy.

Jeśli masz wybór, zalecałbym używanie, DATETIME2gdy tylko jest to możliwe. Nie widzę żadnych korzyści DATETIME(z wyjątkiem kompatybilności wstecznej) - będziesz miał mniej problemów (daty są poza zakresem i takie kłopoty).

Plus: jeśli potrzebujesz tylko daty (bez części czasu), użyj DATE - jest tak samo dobra, jak DATETIME2i oszczędza miejsce! :-) To samo dotyczy tylko czasu - użyj TIME. Po to są te typy!

marc_s
źródło
158
Zachowaj ostrożność, dodając wartość .NET DateTime jako parametr do SqlCommand, ponieważ lubi zakładać, że jest to stary typ daty i godziny, i wystąpi błąd, jeśli spróbujesz zapisać wartość DateTime poza zakresem 1753-9999 lat chyba że jawnie określisz typ jako System.Data.SqlDbType.DateTime2 dla SqlParameter. W każdym razie datetime2 jest świetny, ponieważ może przechowywać dowolną wartość, która może być przechowywana w typie .NET DateTime.
Triynko
10
@marc_s - Czy nie po to jest null?
JohnFx,
8
@JohnFX - tutaj trochę za późno - ale nie ustawisz daty i godziny na zero. użyłbyś Nullable <datetime> lub datetime? który dobrze radzi sobie z wartością null - a przy mapowaniu do proc po prostu zrobiłby param.value = someDateTime ?? DBValue.Null Jego niefortunne, że jesteśmy skazani na typ danych z wielu po to - po prostu wydaje się więc „rodzajowe”:)
Adam Tuliper - MSFT
69
Lol, właśnie próbowałem głosować za własnym komentarzem (powyżej), zanim zdałem sobie sprawę, że to mój własny komentarz (napisany ponad rok temu). Nadal mam do czynienia z głupią decyzją projektową środowiska .NET, aby TRUNCATE domyślnie TRUNCATE wszystkie wartości DateTime, gdy są przekazywane jako SqlParameters, chyba że jawnie ustawisz je na bardziej precyzyjną SqlDbType.DateTime2. Tyle o automatycznym wnioskowaniu o poprawnym typie. Naprawdę powinni byli uczynić tę zmianę przejrzystą, zastępując mniej precyzyjną, mniej wydajną implementację o ograniczonym zasięgu i zachować oryginalną nazwę typu „datetime”. Zobacz także stackoverflow.com/q/8421332/88409
Triynko
5
@marc_s Czy nie po to Nullable<DateTime>jest?
ChrisW,
207

datetime2 wygrywa w większości aspektów z wyjątkiem (kompatybilności ze starymi aplikacjami)

  1. większy zakres wartości
  2. lepsza dokładność
  3. mniejsze miejsce do przechowywania (jeśli określona jest opcjonalna precyzja określona przez użytkownika)

Porównanie typów danych Data i godzina SQL - datetime, datetime2, date, TIME

proszę zwrócić uwagę na następujące punkty

  • Składnia
    • datetime2 [(ułamek sekundowy precyzji => Spójrz poniżej rozmiaru pamięci)]
  • Precyzja, skala
    • 0 do 7 cyfr z dokładnością do 100ns.
    • Domyślna dokładność to 7 cyfr.
  • Rozmiar przechowywania
    • 6 bajtów dla dokładności mniejszej niż 3;
    • 7 bajtów dla dokładności 3 i 4.
    • Każda inna precyzja wymaga 8 bajtów .
  • DateTime2 (3) ma taką samą liczbę cyfr jak DateTime, ale wykorzystuje 7 bajtów pamięci zamiast 8 bajtów ( SQLHINTS- DateTime Vs DateTime2 )
  • Dowiedz się więcej o datetime2 (artykuł MSDN w języku Transact-SQL)

źródło obrazu: Zestaw szkoleniowy MCTS (egzamin 70-432): Microsoft® SQL Server® 2008 - Implementacja i konserwacja Rozdział 3: Tabele -> Lekcja 1: Tworzenie tabel -> strona 66

Iman
źródło
7
Dziękujemy za pokazanie, że statystyki +1 za to datetime2są niesamowite (Zwycięzca)
Pankaj Parkar
2
@Iman Abidi: Według komentarza Oskara Berggrena z 10 września 2014 r. O 15:51 w artykule „SQLHINTS- DateTime Vs DateTime2”, do którego się odwołujesz: „datetime2 (3) NIE jest taki sam jak datetime. Będą miały ten sam numer cyfr, ale dokładność datetime wynosi 3,33 ms, podczas gdy dokładność datetime 2 (3) wynosi 1 ms. ”
Tom
1
@PankajParkar: Woah, nie tak szybko. Możesz zajrzeć do sekcji minusów mojej odpowiedzi z dnia 7/10/17 poniżej.
Tom
W jaki sposób datetime2wykorzystuje mniej miejsca do przechowywania, datetimea jednocześnie oferuje większy zasięg i większą precyzję?
Dai
107

Zgadzam się z @marc_s i @Adam_Poward - DateTime2 jest preferowaną metodą przechodzenia do przodu. Ma szerszy zakres dat, wyższą precyzję i zużywa mniej więcej tyle samo miejsca (w zależności od precyzji).

Jedną rzeczą dyskusja brakowało jednak ...
@Marc_s stwierdza: Both types map to System.DateTime in .NET - no difference there. Jest to poprawne, jednak odwrotność nie jest prawdziwa ... i ma to znaczenie przy wyszukiwaniu zakresu dat (np. „Znajdź wszystkie rekordy zmodyfikowane 05.05.2010”).

Wersja .NET Datetimema podobny zasięg i precyzję do DateTime2. Podczas mapowania .net w Datetimedół do starego SQL DateTimewystępuje niejawne zaokrąglenie . Stary SQL DateTimema dokładność do 3 milisekund. Oznacza to, że 11:59:59.997jest tak blisko, jak to możliwe, do końca dnia. Wszystko wyższe jest zaokrąglane do następnego dnia.

Spróbuj tego :

declare @d1 datetime   = '5/5/2010 23:59:59.999'
declare @d2 datetime2  = '5/5/2010 23:59:59.999'
declare @d3 datetime   = '5/5/2010 23:59:59.997'
select @d1 as 'IAmMay6BecauseOfRounding', @d2 'May5', @d3 'StillMay5Because2msEarlier'

Unikanie tego niejawnego zaokrąglania jest istotnym powodem przejścia na DateTime2. Domniemane zaokrąglanie dat wyraźnie powoduje zamieszanie:

EBarr
źródło
14
Możesz także uniknąć tego zaokrąglania, nie próbując i tak znaleźć „końca” dnia. > = 5 maja i <6 maja jest znacznie bezpieczniejszy i będzie działał na każdym typie daty / godziny (z wyjątkiem oczywiście CZASU). Sugeruj także unikanie regionalnych, niejednoznacznych formatów, takich jak m / d / rrrr.
Aaron Bertrand
2
@AaronBertrand - całkowicie się zgadzam, ale patrząc na liczbę pytań mamy sprawę, którą warto opisać.
EBarr
1
Dlaczego zmieniłeś się z 20100505na 5/5/2010? Poprzedni format będzie działał z dowolnym regionem w SQL Server. Ten ostatni się załamie: SET LANGUAGE French; SELECT Convert(datetime, '1/7/2015')ups:2015-07-01 00:00:00.000
ErikE
1
@EBarr: Re. „DateTime2 jest preferowaną metodą posuwającą się naprzód. Ma szerszy zakres dat, wyższą precyzję i zużywa mniej więcej tyle samo miejsca (w zależności od precyzji”): zdecydowanie się nie zgadzam. Zobacz sekcję „Wady” mojej odpowiedzi z dnia 7/10/17 poniżej Krótko mówiąc, korzyści te są prawdopodobnie niepotrzebne (poza aplikacjami inżynieryjnymi / naukowymi) i dlatego nie są warte utraty DUŻO bardziej potrzebnych, o wiele łatwiejszych (nawet biorąc pod uwagę obejścia) możliwości niejawnej / jawnej konwersji na zmiennoprzecinkowe ( Liczba dni, w tym, jeśli dotyczy, ułamki od minimalnej daty i godziny) wartość +, - i śr.
Tom
20

Prawie wszystkie odpowiedzi i komentarze były bardzo mocne dla zalet i lekkie dla wad. Oto podsumowanie wszystkich dotychczasowych zalet i wad oraz niektóre kluczowe wady (w punkcie 2 poniżej), o których widziałem tylko raz lub wcale.

  1. Plusy:

1.1 Bardziej zgodny z ISO (ISO 8601) (choć nie wiem, jak to się dzieje w praktyce).

1.2 Większy zakres (1/1/0001 do 12/31/9999 vs. 1/1 / 1753-12 / 31/9999) (chociaż dodatkowy zakres, wszystkie przed rokiem 1753, prawdopodobnie nie będzie stosowany, z wyjątkiem np. w aplikacjach historycznych, astronomicznych, geologicznych itp.).

1.3 Dokładnie pasuje do zakresu zakresu typu .NET DateTime(chociaż oba konwertują tam iz powrotem bez specjalnego kodowania, jeśli wartości mieszczą się w zakresie i precyzji typu docelowego, z wyjątkiem Con # 2.1 poniżej, w przeciwnym razie wystąpi błąd / zaokrąglenie).

1.4 Większa precyzja (100 nanosekund, czyli 0,000,000,1 sek. Vs. 3,33 milisekunda, czyli 0,003,33 sek.) (Chociaż dodatkowa precyzja prawdopodobnie nie zostanie wykorzystana, z wyjątkiem np. Aplikacji inżynierskich / naukowych).

1.5 Po skonfigurowaniu dla podobnej (jak w 1 milisek nie „takiej samej” (jak w 3,33 milisek), jak twierdzi Iman Abidi) precyzji, ponieważ DateTimezużywa mniej miejsca (7 vs 8 bajtów), ale wtedy oczywiście straciłbyś precyzja korzyści, która prawdopodobnie jest jedną z dwóch (druga to zakres) najbardziej reklamowana, choć prawdopodobnie niepotrzebnymi korzyściami).

  1. CONS:

2.1 Podczas przekazywania parametru do .NET SqlCommand, musisz określić, System.Data.SqlDbType.DateTime2czy możesz przekazać wartość poza DateTimezakresem i / lub precyzją SQL Servera , ponieważ domyślnie jest to System.Data.SqlDbType.DateTime.

2.2 Nie można go niejawnie / łatwo przekonwertować na zmiennoprzecinkową wartość liczbową (liczbę dni od minimalnej daty i godziny), aby wykonać następujące czynności w wyrażeniach programu SQL Server za pomocą wartości liczbowych i operatorów:

2.2.1 dodaj lub odejmij # dni lub częściowe dni. Uwaga: użycie DateAddfunkcji jako obejścia nie jest trywialne, gdy trzeba rozważyć wiele, jeśli nie wszystkie części daty i godziny.

2.2.2 weź pod uwagę różnicę między dwiema datami dla celów obliczenia „wieku”. Uwaga: Zamiast tego nie można po prostu użyć DateDifffunkcji programu SQL Server , ponieważ nie oblicza się, agejak większość ludzi by się spodziewała, gdyby dwie daty i godziny przekroczyły granicę daty / godziny kalendarza / zegara jednostek określonych, nawet jeśli to tylko ułamek tej jednostki, zwróci różnicę jako 1 tej jednostki w stosunku do 0. Na przykład, DateDiffw Daydwóch datach tylko 1 milisekunda od siebie zwróci 1 w stosunku do 0 (dni), jeśli te daty są w różne dni kalendarzowe (tj. „1999-12-31 23: 59: 59.9999999” i „2000-01-01 00: 00: 00.0000000”). Ta sama różnica 1 milisekundy data-godzina, jeśli zostanie przeniesiona tak, aby nie przekraczała dnia kalendarzowego, zwróci „DateDiff” w Daywartości 0 (dni).

2.2.3 weź Avgpod uwagę daty i godziny (w zapytaniu zbiorczym), po prostu konwertując najpierw na „Float”, a następnie ponownie na DateTime.

UWAGA: Aby przekonwertować DateTime2na wartość liczbową, musisz zrobić coś w rodzaju następującej formuły, która nadal zakłada, że ​​twoje wartości nie są mniejsze niż w roku 1970 (co oznacza, że ​​tracisz cały dodatkowy zakres plus kolejne 217 lat. Uwaga: Możesz nie można po prostu dostosować formuły, aby umożliwić dodatkowy zasięg, ponieważ możesz napotkać problemy z przepełnieniem numerycznym.

25567 + (DATEDIFF(SECOND, {d '1970-01-01'}, @Time) + DATEPART(nanosecond, @Time) / 1.0E + 9) / 86400.0- Źródło: „ https://siderite.dev/blog/how-to-translate-t-sql-datetime2-to.html

Oczywiście, można też Castna DateTimepierwszy (i ewentualnie z powrotem do DateTime2), ale trzeba by stracić dokładność i zasięg (wszystkie poprzedzające rok 1753) Korzyści z DateTime2vs. DateTimektóre są naprawde 2 największe i również w tym samym czasie prolly 2 najmniej prawdopodobne potrzeby, które nasuwają pytanie, po co z niego korzystać, gdy tracisz niejawną / łatwą konwersję na zmiennoprzecinkową liczbę (liczbę dni) w celu dodania / odjęcia / korzyści związanych z wiekiem (vs. DateDiff) / Avgcieląt, która jest duża z mojego doświadczenia.

Przy okazji, Avgdata jest ważnym (lub przynajmniej powinna być) ważnym przypadkiem użycia. a) Oprócz użycia w uzyskiwaniu średniego czasu trwania, gdy daty i godziny (od wspólnej podstawowej daty i godziny) są używane do reprezentowania czasu trwania (powszechna praktyka), b) przydatne jest również uzyskanie statystyki typu deski rozdzielczej na temat średniej daty czas znajduje się w kolumnie daty i godziny zakresu / grupy wierszy. c) Standardowe (lub przynajmniej powinno być standardowe) zapytanie ad-hoc do monitorowania / rozwiązywania problemów z wartościami w kolumnie, które mogą nie być ważne / już dłużej i / lub mogą wymagać wycofania, to podać dla każdej wartości liczbę wystąpień oraz (jeśli są dostępne), że Min, Avgi Maxznaczków data-czas związany z tą wartością.

Tomek
źródło
1
Podobnie jak pogląd contrarian - wskazuje stronę c # równania. W połączeniu ze wszystkimi innymi „profesjonalistami” pozwoli ludziom dokonać dobrego wyboru na podstawie tego, gdzie chcą wziąć ból.
EBarr
1
@EBarr: Tylko część Cons # 1 mojego „” contrarian view ”„ ”wskazuje stronę c # równania”. Reszta (wady nr 2.2.1 - 2.2.3), które, jak powiedziałem, są o wiele bardziej prawdopodobnymi potrzebnymi korzyściami DateTime, są związane z wpływem na zapytania i instrukcje SQL Server.
Tom
Do 2.2.1 - za arytmetykę dat uważa się niebezpieczną praktykę, a preferowanym sposobem jest zawsze używanie DateAdd i powiązanych funkcji. To jest najlepsza praktyka. Wykonywanie arytmetyki dat wiąże się z poważnymi zobowiązaniami, z których nie najmniej ważne, że nie działa ona w przypadku większości typów dat. Kilka artykułów: sqlservercentral.com/blogs/… sqlblog.org/2011/09/20/…
RBerman
@RBerman: Re. „niebezpieczne”: Jest niebezpieczne tylko w przypadku niektórych typów dat (takich jak DateTime2już wspomniane (ze względu na duże ryzyko przepełnienia)). Re. „nie działa w przypadku większości typów dat”: potrzebujesz go tylko do pracy z jednym, a większość dat w większości aplikacji prawdopodobnie nigdy nie będzie musiała być konwertowana na inny typ daty przez cały okres ich użytkowania (z wyjątkiem może, jak wspomniałem, również , DateTime2aby DateTime(np. wykonać „arytmetykę w datach”; P). Biorąc to pod uwagę, nie jest warte całego dodatkowego kodowania w nie tylko zaprogramowanych, ale również doraźnych zapytaniach badawczych, aby użyć nie-arytmetycznego typu daty.
Tom
15

DateTime2 sieje spustoszenie, jeśli jesteś programistą Access, który próbuje napisać Now () w odpowiednim polu. Właśnie wykonałem migrację Access -> SQL 2008 R2 i umieściłem wszystkie pola daty i godziny jako DateTime2. Dołączanie rekordu za pomocą Now () jako wartości zbombardowanej. W dniu 01.01.2012 14:53:04 było w porządku, ale nie w dniu 01.10.2012 14:53:04 PM.

Kiedyś postać zrobiła różnicę. Mam nadzieję, że to komuś pomoże.

Rhett A Brown
źródło
15

Oto przykład, który pokaże różnice w wielkości pamięci (bajtach) i precyzji między smalldatetime, datetime, datetime2 (0) i datetime2 (7):

DECLARE @temp TABLE (
    sdt smalldatetime,
    dt datetime,
    dt20 datetime2(0),
    dt27 datetime2(7)
)

INSERT @temp
SELECT getdate(),getdate(),getdate(),getdate()

SELECT sdt,DATALENGTH(sdt) as sdt_bytes,
    dt,DATALENGTH(dt) as dt_bytes,
    dt20,DATALENGTH(dt20) as dt20_bytes,
    dt27, DATALENGTH(dt27) as dt27_bytes FROM @temp

który zwraca

sdt                  sdt_bytes  dt                       dt_bytes  dt20                 dt20_bytes  dt27                         dt27_bytes
2015-09-11 11:26:00  4          2015-09-11 11:25:42.417  8         2015-09-11 11:25:42  6           2015-09-11 11:25:42.4170000  8

Więc jeśli chcę przechowywać informacje do drugiej - ale nie do milisekundy - mogę zapisać 2 bajty każdy, jeśli użyję datetime2 (0) zamiast datetime lub datetime2 (7).

Baodad
źródło
10

podczas gdy zwiększa się precyzja w datetime2 , niektórzy klienci nie obsługują daty , godziny ani datetime2 i zmuszają cię do konwersji na literał łańcuchowy. W szczególności Microsoft wspomina o problemach ODBC, OLE DB, JDBC i SqlClient „niższego poziomu” z tymi typami danych i ma wykres pokazujący, w jaki sposób każdy może odwzorować typ.

Jeśli cenisz zgodność zamiast precyzji, użyj datetime

Pięść furii
źródło
10

Stare pytanie ... Ale chcę dodać coś, co nie zostało tu jeszcze powiedziane ... (Uwaga: To moja własna obserwacja, więc nie pytaj o żadne odniesienia)

Datetime2 jest szybszy, gdy jest używany w kryteriach filtrowania.

TLDR:

W SQL 2016 miałem tabelę ze sto tysiącami wierszy i kolumnę daty i godziny ENTRY_TIME, ponieważ wymagane było przechowywanie dokładnego czasu do sekund. Podczas wykonywania złożonego zapytania z wieloma złączeniami i podpytaniem, gdy użyłem klauzuli where jako:

WHERE ENTRY_TIME >= '2017-01-01 00:00:00' AND ENTRY_TIME < '2018-01-01 00:00:00'

Zapytanie początkowo działało poprawnie, gdy były setki wierszy, ale gdy liczba wierszy wzrosła, zapytanie zaczęło dawać ten błąd:

Execution Timeout Expired. The timeout period elapsed prior
to completion of the operation or the server is not responding.

Usunąłem klauzulę where i nieoczekiwanie zapytanie zostało uruchomione w ciągu 1 sekundy, chociaż teraz WSZYSTKIE wiersze dla wszystkich dat zostały pobrane. Uruchamiam wewnętrzne zapytanie z klauzulą ​​where i zajęło 85 sekund, a bez klauzuli zabrało 0,01 sekundy.

Spotkałem się tutaj z wieloma wątkami dotyczącymi tego problemu jako wydajności filtrowania według czasu i daty

Zoptymalizowałem trochę zapytanie. Ale prawdziwą prędkością, jaką uzyskałem, była zmiana kolumny datetime na datetime2.

Teraz to samo zapytanie, które przekroczyło limit czasu, zajmuje mniej niż sekundę.

Twoje zdrowie

MJ Khan
źródło
9

Interpretacja ciągów daty na datetimei datetime2może być również inna, gdy używane są DATEFORMATustawienia spoza USA . Na przykład

set dateformat dmy
declare @d datetime, @d2 datetime2
select @d = '2013-06-05', @d2 = '2013-06-05'
select @d, @d2

Zwraca 2013-05-06(tj. 6 maja) dla datetimei 2013-06-05(tj. 5 czerwca) dla datetime2. Jednak z dateformatustawionym na mdyoba @di @d2wróć 2013-06-05.

datetimeZachowanie wydaje się sprzeczne z dokumentacji MSDN z SET DATEFORMATktórych stwierdza: Niektóre formaty ciągów znaków, na przykład ISO 8601, są interpretowane niezależnie od ustawienia dateformat . Oczywiście nieprawda!

Dopóki mnie to nie ugryzło, zawsze myślałem, że yyyy-mm-dddaty będą obsługiwane właściwie, niezależnie od ustawień języka / ustawień regionalnych.

Richard Fawcett
źródło
2
Nie. Dla ISO 8601 myślę, że miałeś na myśli RRRRMMDD (bez myślników). SET LANGUAGE FRENCH; DECLARE @d DATETIME = '20130605'; SELECT @d;Spróbuj ponownie z myślnikami.
Aaron Bertrand
1
Standard dopuszcza zarówno formaty RRRR-MM-DD, jak i RRRRMMDD do reprezentacji dat kalendarzowych. Myślę, że MSDN powinien bardziej szczegółowo określać, który podzbiór specyfikacji ISO 8601 jest interpretowany niezależnie!
Richard Fawcett
1
Wiem o tym, ale w SQL Server tylko składnia no-dash jest bezpieczna.
Aaron Bertrand
6

Zgodnie z tym artykułem , jeśli chcesz mieć tę samą precyzję DateTime przy użyciu DateTime2, po prostu musisz użyć DateTime2 (3). To powinno dać ci taką samą precyzję, zająć o jeden mniej bajtów i zapewnić rozszerzony zakres.

jKlaus
źródło
Dla jasności jest to ta sama precyzja, co SQL datetime, a nie .NET DateTime.
Sam Rueby,
Zgadza się, założyłem, że wszyscy zrozumieją kontekst, ale warto to wyraźnie powiedzieć.
jKlaus,
4

Właśnie natknąłem się na jeszcze jedną zaletę DATETIME2: pozwala uniknąć błędu w adodbapimodule Pythona , który wybuchnie, jeśli datetimezostanie przekazana standardowa wartość biblioteki, która ma niezerowe mikrosekundy dla DATETIMEkolumny, ale działa dobrze, jeśli kolumna jest zdefiniowana jako DATETIME2.

Bob Kline
źródło
0
Select ValidUntil + 1
from Documents

Powyższy kod SQL nie będzie działać z polem DateTime2. Zwraca błąd „Zderzenie typu argumentu: datetime2 jest niezgodny z int”

Dodanie 1, aby uzyskać następny dzień, jest czymś, co programiści robią z datami od lat. Teraz Microsoft ma super nowe pole datetime2, które nie obsługuje tej prostej funkcji.

„Użyjmy tego nowego typu, który jest gorszy od starego”, nie sądzę!

Paul McCarthy
źródło
2
Tylko tak jesteśmy jasne, tu datetimei datetime2typy danych zostały wprowadzone zarówno w SQL Server 2008 można również uzyskać Operand type clash: date is incompatible with intod datetypu, który istnieje od dnia kropką. dateadd(dd, 1, ...)Jednak wszystkie trzy typy danych działają dobrze .
AlwaysLearning
2
To nie jest jasne. Mam bazę danych SQLServer 2005 z polem daty i godziny.
Paul McCarthy,
0

Myślę, że DATETIME2to lepszy sposób na przechowywanie date, ponieważ ma większą wydajność niż DATETIME. W SQL Server 2008można użyć DATETIME2, przechowuje datę i godzinę, trwa 6-8 bytesdo przechowywania i ma precyzję 100 nanoseconds. Każdy, kto potrzebuje większej precyzji czasu, będzie chciał DATETIME2.

James
źródło