DateTime.Now.AddSeconds(60)
作为absoluteExpiration参数的值。
我想过,相对于DateTime.UtcNow计算会更正确[因为如果夏令时开始在从现在到到期点之间的间隔时间,没有歧义]。
在介绍DateTimeKind之前,我已经猜到,在缓存管理中有一些丑陋的黑客,如果时间不是UTC时间,它会做一些适当的事情。
在.NET 2.0和更高版本中,我猜测它应该处理DateTime.UtcNow.AddSeconds(60)计算的DateTime,因为它有DateTime.Kind在其推理中用作输入。
我已经自信地使用DateTime.UtcNow作为基础多年,但是没能提出一个理由,这是绝对正确的事情,没有任何东西指出文件已被高度误导4年。
问题?
>尽管有很多bingage和谷歌我没有能够找到任何权威的讨论,从MS – 任何人都可以找到一些关于这一点?
>有什么原因为什么使用UtcNow不会更正确和/或安全?
(是的,我可以细读源和/或反射器的来源,但我正在寻找一个完整的吹一吹下来!)
解决方法
如果您在本地时间指定绝对到期,您仍然有一个.NET 2.0中的问题。
在夏令时结束时的一小时内,您的当地时间不明确,因此您可能会得到意想不到的结果,即绝对到期时间可能比预期长一个小时。
在欧洲,夏令时在2009年10月25日的02:00结束。下面的示例说明如果您在01:59将项目放置在缓存中,且过期时间为2分钟,则该项目将在缓存中保留一小时, 2分钟。
DateTime startTime = new DateTime(2009,10,25,1,59,0); DateTime endTime = startTime.AddMinutes(2); // end time is two minutes after start time DateTime startUtcTime = startTime.ToUniversalTime(); DateTime endUtcTime = endTime.ToUniversalTime(); // end UTC time is one hour and two minutes after start UTC time Console.WriteLine("Start UTC time = " + startUtcTime.ToString()); Console.WriteLine("End UTC time = " + endUtcTime.ToString());
.NET 2.0或更高版本的解决方法是指定Ruben指出的UTC中的绝对到期时间。
微软应该建议使用UTC的绝对到期的例子,但我想有可能混乱,因为这个建议只适用于.NET 2.0和更高版本。
编辑
从评论:
But the exposure only occurs if the
conversion happens during the overlap.
The single conversion actually taking
place is when you lodge the item with
Cache.Add
该问题只会发生,如果您在缓存中插入一个项目AbsoluteExpiration时间在本地时间在一个模糊的小时在夏令时结束时。
例如,如果您的本地时区是中欧(冬季GMT 1,夏季GMT 2),并且您在2009年10月25日01:59:00执行以下代码:
DateTime absoluteExpiration = DateTime.Now.AddMinutes(2); Cache.Add(... absoluteExpiration ...)
那么项目将保留在缓存中一小时两分钟,而不是通常预期的两分钟。这对于一些高度时间关键的应用(例如股票行情,航空公司出发板)来说可能是个问题。
这里发生的是(假设欧洲时间,但原则是相同的任何时区):
> DateTime.Now = 2009-10-25 01:59:00 local。 local = GMT 2,因此UTC = 2009-10-24 23:59:00
> .AddMinutes(2)= 2009-10-25 02:01:00 local。 local = GMT 1,因此UTC = 2009-11-25 01:01:00
> Cache.Add内部将到期时间转换为UTC(2009-11-25 01:01:00),因此到期时间比当前UTC时间(23:59:00)提前一小时两分钟。
如果您使用DateTime.UtcNow代替DateTime.Now,缓存过期将是两分钟(.NET 2.0或更高版本):
DateTime absoluteExpiration = DateTime.UtcNow.AddMinutes(2); Cache.Add(... absoluteExpiration ...)
从评论:
Or am I missing something?
不你不是。您的分析是现货,如果您的应用程序是时间关键的,并在DST期间的这段时间运行,你是正确的使用DateTime.UtcNow。
Ruben的回答中的陈述:
you’re safe to use either as long as the Kind on the time you supply is set
是不正确的。