简体   繁体   English

.NET 核心中的日期时间精度

[英]DateTime precision in .NET core

Following Eric Lippert's post years back on precision of DateTime , I ran his test on .netcore and .NET Framework 4.5.2, on the same machine with Windows 10.继 Eric Lippert 几年前关于DateTime精度的帖子之后,我在装有 Windows 10 的同一台机器上在 .netcore 和 .NET Framework 4.5.2 上运行了他的测试。

        var n = 1000;
        int i = 0;
        long[] diffs = new long[n];
        while (i++ < n-1)
        {
            if (ticks != DateTime.Now.Ticks)
            {
                var newTicks = DateTime.UtcNow.Ticks;
                var diff = newTicks - ticks;
                diffs[i] = diff;
                ticks = newTicks;
            }
        }
        foreach (var d in diffs)
        {
            if (d == 0)
                Console.WriteLine("same");
            else
                Console.WriteLine(d);

        }

The result on .NET framework 4.5.2 was as expected: some random "same" in output which means DateTime is not precise to some sub-levels. .NET 框架 4.5.2 上的结果如预期:输出中有一些随机的“相同”,这意味着DateTime对某些子级别不精确。

However, the result on .NET core was totally different: no "same" in output.但是,在 .NET 核心上的结果完全不同:输出中没有“相同”。 Not two Ticks had the same value.不是两个Ticks具有相同的值。

What would be the explanation?会有什么解释?

The explanation would be, that dot net asks the underlying operating system for the current time.解释是,dot net 向底层操作系统询问当前时间。 The operating system asks the underlying hardware.操作系统询问底层硬件。 In ancient times the hardware clock (RTC) on the motherboard used to update itself once in about 15 milli seconds.在古代,主板上的硬件时钟 (RTC) 过去常常每 15 毫秒更新一次。 That number was derived from the 60Hz AC line frequency in US which the power grid maintained sufficient accurately.该数字源自美国电网保持足够准确的 60Hz 交流线路频率。 Remember those were the days of "slow" computers and designers tried to squeeze in every bit of performance they could.请记住,那是“缓慢”计算机的时代,设计人员试图尽其所能地发挥其性能。 So the OS did not consult RTC everytime someone asked for time and passed a cached copy of the value - which is updated very infrequently.因此,操作系统不会在每次有人询问时间并传递值的缓存副本时咨询 RTC - 很少更新。

Somewhere down the line, the motherboard evolved and the RTCs became more precise.后来,主板不断发展,RTC 变得更加精确。 But the OS and all the things on top of it did not feel the need for it.但是操作系统和它上面的所有东西并不觉得需要它。 Remember h/w evolved far faster than software and even till day, consumer grade software waste a large fraction of raw h/w capability.请记住,硬件的发展速度远远快于软件,甚至直到今天,消费级软件都浪费了很大一部分原始硬件能力。 So when dot net framework asked OS for time, it got back the imprecise data even when the h/w was capable.因此,当 dot net framework 向操作系统询问时间时,即使硬件有能力,它也会取回不精确的数据。 The accuracy did evolve from 15ms to below 1ms, but that was it.精度确实从 15 毫秒发展到 1 毫秒以下,但仅此而已。

Come windows 8 (server 2012), it was finally realized that (1) applications could do better with more precise time (2) computers are fast so consulting RTC everytime is no longer a problem (3) a large population of programmers and programs are used to and actually rely on the imprecise time behavior.来到 Windows 8(服务器 2012),终于意识到 (1) 应用程序可以在更精确的时间下做得更好 (2) 计算机速度很快,因此每次咨询 RTC 不再是问题 (3) 大量的程序员和程序过去并且实际上依赖于不精确的时间行为。 So they (win 8) went on to introduce a new marginally slower mechanism to obtain the most precise time data, but left the original implementation unchanged.所以他们(win 8)继续引入一种新的稍微慢一点的机制来获得最精确的时间数据,但保持原始实现不变。

Dot net had always used the older and imprecise OS function GetSystemTimeAsFileTime and when a new cousin GetSystemTimePreciseAsFileTime appeared in win 8, dot net chose to go the backward compatible way and did nothing. dot net 一直使用较旧且不精确的 OS 函数GetSystemTimeAsFileTime ,当新表亲GetSystemTimePreciseAsFileTime出现在 win 8 中时,dot net 选择了向后兼容的方式,什么也没做。

Dot net core is a fresh rewrite of many core features and now leverages the high precision data source.点网核心是对许多核心功能的全新重写,现在利用了高精度数据源。

Edit编辑

If the current time is 13:14:15:123456 , there is still no guarantee that the real true time, as seen by the physicists and astronomers is that.如果当前时间是13:14:15:123456 ,仍然无法保证物理学家和天文学家所看到的真实时间就是那个。 Your computer is not an atomic clock.您的计算机不是原子钟。 And certainly not a well synchronized clock.当然不是一个同步良好的时钟。 The only thing it means is that if two events happened at different timestamps then one event happened certainly before the another.它唯一的意思是,如果两个事件发生在不同的时间戳,那么一个事件肯定会先于另一个事件发生。 In older computers, rate of generation of events (ex logs, files, database txns etc) was lower and so there was low chance that sequential events would be assigned same timestamps.在较旧的计算机中,事件(例如日志、文件、数据库 txns 等)的生成率较低,因此为连续事件分配相同时间戳的可能性很小。 This new time system caters to modern high rate activities so that you can mark sequential events as different.这个新的时间系统迎合了现代高频率活动,因此您可以将连续事件标记为不同。 Still for two very close events, there will always be a chance of same timestamp.仍然对于两个非常接近的事件,总会有相同时间戳的机会。 That is eventually unavoidable.这最终是不可避免的。 If you need nanosecond level measurement (why) you need different tools like Stopwatch and not System.DateTime .如果您需要纳秒级测量(为什么),您需要不同的工具,如Stopwatch而不是System.DateTime

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM