Sqlserver
 sql >> Database >  >> RDS >> Sqlserver

Perché Datediff tra GETDATE() e SYSDATETIME() in millisecondi è sempre diverso?

Sono due chiamate di funzione diverse che possono restituire due volte diverse.

Inoltre GETDATE restituisce un datetime tipo di dati che ha solo una precisione di 3-4 ms mentre SYSDATETIME() restituisce un datetime2(7) tipo di dati.

Anche se entrambe le chiamate dovessero tornare esattamente nello stesso momento, potresti riscontrare il problema che stai riscontrando a causa dell'arrotondamento.

DECLARE @D1 DATETIME2 = '2012-08-18 10:08:40.0650000'
DECLARE @D2 DATETIME = @D1 /*Rounded to 2012-08-18 10:08:40.067*/
SELECT DATEDIFF(ms, @D1 , @D2) /*Returns 2*/

L'altra risposta non è corretta se si sostituisce in GETDATE() la funzione viene chiamata solo una volta come si può dimostrare dal seguito.

WHILE DATEDIFF(ms, GETDATE() , GETDATE()) = 0 
PRINT 'This will not run in an infinite loop'

Quando si esegue un ciclo sul desktop di Windows XP con GETDATE() e SYSDATETIME Posso anche vedere risultati che indicano che potrebbe succedere anche qualcos'altro. Forse chiamando un'API diversa.

CREATE TABLE #DT2
  (
     [D1] [DATETIME2](7),
     [D2] [DATETIME2](7)
  )

GO

INSERT INTO #DT2
VALUES(Getdate(), Sysdatetime())

GO 100

SELECT DISTINCT [D1],
                [D2],
                Datediff(MS, [D1], [D2]) AS MS
FROM   #DT2

DROP TABLE #DT2 

Esempi di risultati di seguito

+-----------------------------+-----------------------------+-----+
|             D1              |             D2              | MS  |
+-----------------------------+-----------------------------+-----+
| 2012-08-18 10:16:03.2500000 | 2012-08-18 10:16:03.2501680 |   0 |
| 2012-08-18 10:16:03.2530000 | 2012-08-18 10:16:03.2501680 |  -3 |
| 2012-08-18 10:16:03.2570000 | 2012-08-18 10:16:03.2501680 |  -7 |
| 2012-08-18 10:16:03.2600000 | 2012-08-18 10:16:03.2501680 | -10 |
| 2012-08-18 10:16:03.2630000 | 2012-08-18 10:16:03.2501680 | -13 |
| 2012-08-18 10:16:03.2630000 | 2012-08-18 10:16:03.2657914 |   2 |
| 2012-08-18 10:16:03.2670000 | 2012-08-18 10:16:03.2657914 |  -2 |
| 2012-08-18 10:16:03.2700000 | 2012-08-18 10:16:03.2657914 |  -5 |
| 2012-08-18 10:16:03.2730000 | 2012-08-18 10:16:03.2657914 |  -8 |
| 2012-08-18 10:16:03.2770000 | 2012-08-18 10:16:03.2657914 | -12 |
| 2012-08-18 10:16:03.2800000 | 2012-08-18 10:16:03.2814148 |   1 |
+-----------------------------+-----------------------------+-----+

Le righe di interesse sono

| 2012-08-18 10:16:03.2600000 | 2012-08-18 10:16:03.2501680 | -10 |
| 2012-08-18 10:16:03.2630000 | 2012-08-18 10:16:03.2501680 | -13 |

Questa discrepanza è troppo grande per essere un problema di arrotondamento e non può essere solo un problema di tempistica con un ritardo tra la chiamata delle due funzioni poiché il problema esiste su più di una riga che GETDATE segnala 10:16:03.26X mentre SYSDATETIME segnala 10:16:03.250