0

我试图以毫秒为单位DatediffGETDATE()SYSDATETIME()

SELECT DATEDIFF(ms, GETDATE() , SYSDATETIME());        

我得到的结果是0or 1or 2or 3。造成这种差异的原因是什么?

看到这个小提琴

4

3 回答 3

9

它们是两个不同的函数调用,可以返回两个不同的时间。

另外GETDATE返回一个datetime只有 3-4 毫秒精度的数据类型,而SYSDATETIME()返回一个datetime2(7)数据类型。

即使两个调用在完全相同的时间返回,您也可以看到由于四舍五入而遇到的问题。

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*/

另一个答案是不正确的,如果你在GETDATE()函数中替换只调用一次,如下所示。

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

在我的 Windows XP 桌面上运行循环时GETDATE()SYSDATETIME我还可以看到结果表明可能还会发生其他事情。也许调用不同的 API。

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 

下面的示例结果

+-----------------------------+-----------------------------+-----+
|             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 |
+-----------------------------+-----------------------------+-----+

感兴趣的行是

| 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 |

这种差异太大而不能成为一个舍入问题,并且不能只是一个时间问题,因为该问题存在于多个报告的行上,而报告的两个函数GETDATE之间10:16:03.26X存在SYSDATETIME延迟10:16:03.250

于 2012-08-18T09:31:16.143 回答
1

它们不同是因为这两个函数不能同时(同时)调用。运行的其他进程可能会影响时间。它们可能因数量不同而不同的原因有很多。

如果你用两次调用来做同样的事情GetDate(),它们不会产生任何差异,因为数据库引擎足够聪明,可以确定它们是相同的事情并重用结果。但是,使用GetDate()andSysDateTime()是不同的,因为它们不是相同的代码路径(它们做不同的事情)。

可以这样想:如果你看到1 + 2and 1 + 2,很容易看出第一个表达式和第二个表达式是一样的,所以你只需要计算一次。如果将其更改为1 + Rand()and 1 + Rand(),您将无法知道这两个不同的调用Rand()将返回什么,因此您必须分别进行计算。

于 2012-08-18T05:26:18.180 回答
-1

这种差异是 PRECISION 和 RESOLUTION 之间差异的一个很好的例子(让我们暂时将 ACCURACY 放在一边)。GETDATE() 返回一个带有(显然)精确到毫秒的 DATETIME,但是,如果你把它放在一个紧密的循环中,你会发现返回的下一个不同的值是几毫秒后;它每秒只能返回大约 300 个不同的值,因为它的分辨率只有大约 3 或 4 毫秒。在此处阅读有关此内容的更多信息这是 DATETIME 数据类型的设计功能/妥协。

于 2017-02-06T19:26:15.227 回答