C# 与 Unix 时间戳相互转换

标签 c# timezone

我有以下单元测试失败

[Fact]
public void Convert_to_and_from_unix_timestamp()
{
    // Arrange
    var timestamp = 1636579063;
    var date = DateTimeOffset.FromUnixTimeSeconds(timestamp).DateTime;

    // Act
    var unixTimeSeconds = ((DateTimeOffset)date).ToUnixTimeSeconds();

    // Assert
    Assert.Equal(expected: timestamp, actual: unixTimeSeconds);

    // result
    // Expected: 1636579063 // 10/11/2021 21:17:43
    // Actual: 1636575463 // 10/11/2021 20:17:43
}

新的(实际的)Unix 时间戳是负一小时。我的机器时区是 UTC+1。这是否意味着 DateTimeOffset 会自动将我的时区 (UTC+1) 设置为日期时间,并且在转换回时间戳时 DateTimeOffset 正在删除 UTC+1,因此减少了一个小时?如何以两种方式管理时区?

最佳答案

问题出在.DateTime行中的片段

    var date = DateTimeOffset.FromUnixTimeSeconds(timestamp).DateTime;

根据 reference source

private DateTime ClockDateTime {
  get {
    // Here we lose Timezone (Offset) - it just added to m_dateTime
    // Kind is Unspecified, that's why we can restore the fact
    // Offset == 0 and we actually have UTC datetime    
    return new DateTime((m_dateTime + Offset).Ticks, DateTimeKind.Unspecified);
  }
}
 
public DateTime DateTime {
  get {
    return ClockDateTime;
  }
}

.Net 为 .DateTime 创建属性(property)新DateTime带有 Kind == DateTimeKind.Unspecified 的实例,所以你失去了时区(现在 OffsetDateTimeOffset 只是添加DateTime)。

为了更正测试放.UtcDateTime而不是 .DateTime :

    var date = DateTimeOffset.FromUnixTimeSeconds(timestamp).UtcDateTime; 

关于C# 与 Unix 时间戳相互转换,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/69920656/

相关文章:

c# - 在 ASP.NET LoginName 控件中显示全名

c# - Windows 窗体应用程序中未处理的异常

c# - 在 WCF 客户端/服务器应用程序中计算 UTC/本地日期时间转换的最佳方法

timezone - 如何在 ABAP 中将 UTC 时间戳转换为系统日期和时间

mysql - 停止在 tz 更改时自动更改 MySQL 中的日期

node.js - Sails autoCreatedAt 和 autoUpdatedAt 插入比我当前时区向前 5 小时的日期时间

c# - ASP.NET MVC 3 自定义 RouteBase 和 OutputCache

C# 模拟系统崩溃

c# - 在 Razor 中,如何根据元素的属性检查 ViewBag IEnumerable 对象中是否存在对象?

php - 不同时区的每小时日志 PHP 和 MySQL