Instant.Now为NodaTime

我正试图让Jon Skeet(以及其他人)使用Noda Time框架。

我正试图现在存储当前(即时)。 Instant是从长时间刻度创建的,但是现在的Ticks数量是多少呢?

是吗:

Instant now = new Instant(DateTime.Now.ToUniversalTime().Ticks); 

还是?

 Instant now = Instant.FromDateTimeUtc(DateTime.Now.ToUniversalTime()); 

它们是否相同,我甚至做得对吗?

PS,如果Jon回答这个问题 – 我想提出一个Instant.Now属性。

PS2我知道标题包含一个标签,但它不会让我有一个简短的“Instant.Now”标题。

我做了一些研究,似乎NodaTime的方式是根据时钟得到现在的时刻。

如果要使用系统时钟获取当前时间,只需使用SystemClock.Instance.GetCurrentInstant()

但是,不要直接在代码中使用SystemClock.Instance ,而是最好在时间感知类中注入IClock依赖项。

这将允许您:

  • 在运行时为类提供SystemClock.Instance ,因此代码将使用正确的时间
  • 在unit testing期间提供IClock的伪实现,以允许您根据需要调整时间以测试各种场景(如时间的推移)。 有一个NodaTime.Testing项目提供了一个名为FakeClock的类。

我发现这非常有用。 我认为有一些像new Instant()Instant.Now返回当前时间将使得更容易硬编码SystemClock用法,因此缺少NodaTime提供的测试优势。

有关使用NodaTime进行unit testing的更多信息,请参阅此链接 。


关于您的代码示例:它们不等同。

  • Instant.FromDateTimeUtc(DateTime.Now.ToUniversalTime())确实会以UTC Instant.FromDateTimeUtc(DateTime.Now.ToUniversalTime())给你当前的瞬间。
  • new Instant(DateTime.Now.ToUniversalTime().Ticks)将来会给你一个错误的日期,因为BCL的DateTime.Ticks表示自1/1/0001以来的刻度1/1/0001 ,而NodaTime的Instant.Ticks表示数字自1/1/1970以来的蜱虫(见这里的评论)。

SystemClock.Now将当前时间作为Instant值返回:

 Instant now = SystemClock.Instance.Now; 

但您可能需要注意IClock接口文档中的IClock

IClock适用于您需要访问当前时间的任何地方。 虽然直接调用SystemClock.Instance.Now并不严格,但就像调用UtcNow一样 ,强烈建议不要将其作为生产代码的样式。 我们建议为需要它的任何东西提供IClock实例,这允许您使用NodaTime.Testing程序集(或您自己的实现)中的存根时钟编写测试。

举个简单的例子,假设您有一个需要当前时间的Logger类。 而不是直接访问SystemClock ,使用通过其构造函数提供的IClock实例:

 public class Logger { private readonly IClock clock; public Logger(IClock clock) { this.clock = clock; } public void Log(string message) { Instant timestamp = this.clock.Now; // Now log the message with the timestamp... } } 

在生产代码中实例化Logger时,可以为其提供SystemClock.Instance 。 但是在Logger类的unit testing中,你可以给它一个FakeClock