如何将Unix时间戳转换为DateTime,反之亦然?
有这个例子的代码,但是它开始谈论毫秒/纳秒的问题。
MSDN上的同样的问题, 自从C#中的Unix时代以来就是秒 。
这是我到目前为止:
public Double CreatedEpoch { get { DateTime epoch = new DateTime(1970, 1, 1, 0, 0, 0, 0).ToLocalTime(); TimeSpan span = (this.Created.ToLocalTime() - epoch); return span.TotalSeconds; } set { DateTime epoch = new DateTime(1970, 1, 1, 0, 0, 0, 0).ToLocalTime(); this.Created = epoch.AddSeconds(value); } }
这是你需要的:
public static DateTime UnixTimeStampToDateTime( double unixTimeStamp ) { // Unix timestamp is seconds past epoch System.DateTime dtDateTime = new DateTime(1970,1,1,0,0,0,0,System.DateTimeKind.Utc); dtDateTime = dtDateTime.AddSeconds( unixTimeStamp ).ToLocalTime(); return dtDateTime; }
或者,对于Java(这是不同的,因为时间戳以毫秒为单位,而不是秒):
public static DateTime JavaTimeStampToDateTime( double javaTimeStamp ) { // Java timestamp is milliseconds past epoch System.DateTime dtDateTime = new DateTime(1970,1,1,0,0,0,0,System.DateTimeKind.Utc); dtDateTime = dtDateTime.AddMilliseconds( javaTimeStamp ).ToLocalTime(); return dtDateTime; }
DateTime到UNIX时间戳:
public static double DateTimeToUnixTimestamp(DateTime dateTime) { return (TimeZoneInfo.ConvertTimeToUtc(dateTime) - new DateTime(1970, 1, 1, 0, 0, 0, 0, System.DateTimeKind.Utc)).TotalSeconds; }
.NET(v4.6)的最新版本增加了对Unix时间转换的内置支持。 这包括来自和来自Unix时间的时间,以秒或毫秒表示。
- Unix时间在几秒钟内
DateTimeOffset
:
DateTimeOffset dateTimeOffset = DateTimeOffset.FromUnixTimeSeconds(1000);
- Unix时间的
DateTimeOffset
秒数:
long unixTimeStampInSeconds = dateTimeOffset.ToUnixTimeSeconds();
- Unix时间以毫秒为单位
DateTimeOffset
:
DateTimeOffset dateTimeOffset = DateTimeOffset.FromUnixTimeMilliseconds(1000000);
-
DateTimeOffset
到Unix时间(以毫秒为单位):
long unixTimeStampInMilliseconds= dateTimeOffset.ToUnixTimeMilliseconds();
注意:这些方法可以从DateTimeOffset
转换到或来自DateTimeOffset
。 要获取DateTime
表示,只需使用DateTimeOffset.DateTime
属性:
DateTime dateTime = dateTimeOffset.UtcDateTime;
“UTC不会随着季节变化而改变,但是如果时区pipe辖区遵守夏令时(夏令时),则当地时间或国内时间可能会发生变化。例如,UTC比前一天晚5个小时(即当天晚些时候比在美国东海岸的当地时间冬季,但提前4小时,而在那里观察夏令时。
所以这是我的代码:
TimeSpan span = (DateTime.UtcNow - new DateTime(1970, 1, 1, 0, 0, 0, 0,DateTimeKind.Utc)); double unixTime = span.TotalSeconds;
小心! AddSeconds和AddMilliseconds在双精度中断了微秒。 这些版本具有很高的精度。
Unix – > DateTime
public static DateTime UnixTimestampToDateTime(double unixTime) { DateTime unixStart = new DateTime(1970, 1, 1, 0, 0, 0, 0, System.DateTimeKind.Utc); long unixTimeStampInTicks = (long) (unixTime * TimeSpan.TicksPerSecond); return new DateTime(unixStart.Ticks + unixTimeStampInTicks, System.DateTimeKind.Utc); }
DateTime – > Unix
public static double DateTimeToUnixTimestamp(DateTime dateTime) { DateTime unixStart = new DateTime(1970, 1, 1, 0, 0, 0, 0, System.DateTimeKind.Utc); long unixTimeStampInTicks = (dateTime.ToUniversalTime() - unixStart).Ticks; return (double) unixTimeStampInTicks / TimeSpan.TicksPerSecond; }
请参阅IdentityModel.EpochTimeExtensions
public static class EpochTimeExtensions { /// <summary> /// Converts the given date value to epoch time. /// </summary> public static long ToEpochTime(this DateTime dateTime) { var date = dateTime.ToUniversalTime(); var ticks = date.Ticks - new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc).Ticks; var ts = ticks / TimeSpan.TicksPerSecond; return ts; } /// <summary> /// Converts the given date value to epoch time. /// </summary> public static long ToEpochTime(this DateTimeOffset dateTime) { var date = dateTime.ToUniversalTime(); var ticks = date.Ticks - new DateTimeOffset(1970, 1, 1, 0, 0, 0, TimeSpan.Zero).Ticks; var ts = ticks / TimeSpan.TicksPerSecond; return ts; } /// <summary> /// Converts the given epoch time to a <see cref="DateTime"/> with <see cref="DateTimeKind.Utc"/> kind. /// </summary> public static DateTime ToDateTimeFromEpoch(this long intDate) { var timeInTicks = intDate * TimeSpan.TicksPerSecond; return new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc).AddTicks(timeInTicks); } /// <summary> /// Converts the given epoch time to a UTC <see cref="DateTimeOffset"/>. /// </summary> public static DateTimeOffset ToDateTimeOffsetFromEpoch(this long intDate) { var timeInTicks = intDate * TimeSpan.TicksPerSecond; return new DateTimeOffset(1970, 1, 1, 0, 0, 0, TimeSpan.Zero).AddTicks(timeInTicks); } }
为了补充ScottCher的答案,我最近发现自己处在令人讨厌的情况,即在input数据集中任意混合了几秒和几毫秒的UNIX时间戳。 下面的代码似乎处理这个问题:
static readonly DateTime UnixEpoch = new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc); static readonly double MaxUnixSeconds = (DateTime.MaxValue - UnixEpoch).TotalSeconds; public static DateTime UnixTimeStampToDateTime(double unixTimeStamp) { return unixTimeStamp > MaxUnixSeconds ? UnixEpoch.AddMilliseconds(unixTimeStamp) : UnixEpoch.AddSeconds(unixTimeStamp); }
Unix时间转换在.NET Framework 4.6中是新的。
现在,您可以更轻松地将date和时间值转换为.NET Frameworktypes和Unix时间。 例如,在JavaScript客户端和.NET服务器之间转换时间值时,这可能是必需的。 以下API已被添加到DateTimeOffset结构中 :
static DateTimeOffset FromUnixTimeSeconds(long seconds) static DateTimeOffset FromUnixTimeMilliseconds(long milliseconds) long DateTimeOffset.ToUnixTimeSeconds() long DateTimeOffset.ToUnixTimeMilliseconds()
我只是通过比较转换到1/1/1970 w / o本地时间调整find正确的答案;
DateTime date = new DateTime(2011, 4, 1, 12, 0, 0, 0); DateTime epoch = new DateTime(1970, 1, 1, 0, 0, 0, 0); TimeSpan span = (date - epoch); double unixTime =span.TotalSeconds;
DateTime unixEpoch = DateTime.ParseExact("1970-01-01", "yyyy-MM-dd", System.Globalization.CultureInfo.InvariantCulture); DateTime convertedTime = unixEpoch.AddMilliseconds(unixTimeInMillisconds);
当然,可以使unixEpoch
成为一个全局静态的,所以它只需要在你的项目中出现一次,如果UNIX时间在几秒钟内就可以使用AddSeconds
。
走另一条路:
double unixTimeInMilliseconds = timeToConvert.Subtract(unixEpoch).TotalMilliseconds;
截断到Int64和/或根据需要使用TotalSeconds
。
一个Unix tick是1秒(如果我记得的话),而一个.NET tick是100纳秒。
如果您遇到纳秒级的问题,您可能需要尝试使用AddTick(10000000 *值)。
我需要将包含UNIX time
的timeval结构 (秒,微秒)转换为DateTime
而不会丢失精度,并且在这里没有find答案,所以我想我可能会添加我的:
DateTime _epochTime = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); private DateTime UnixTimeToDateTime(Timeval unixTime) { return _epochTime.AddTicks( unixTime.Seconds * TimeSpan.TicksPerSecond + unixTime.Microseconds * TimeSpan.TicksPerMillisecond/1000); }
DateTime到Unix时间戳,包括夏令时(DST)
public static double DateTimeToUnixTimestamp(DateTime dateTime) { double unixTime = (dateTime - new DateTime(1970, 1, 1).ToLocalTime()).TotalSeconds; if(dateTime.IsDaylightSavingTime()) { unixTime -= 3600; } return unixTime; }
对于.NET 4.6及更高版本:
public static class UnixDateTime { public static DateTimeOffset FromUnixTimeSeconds(long seconds) { if (seconds < -62135596800L || seconds > 253402300799L) throw new ArgumentOutOfRangeException("seconds", seconds, ""); return new DateTimeOffset(seconds * 10000000L + 621355968000000000L, TimeSpan.Zero); } public static DateTimeOffset FromUnixTimeMilliseconds(long milliseconds) { if (milliseconds < -62135596800000L || milliseconds > 253402300799999L) throw new ArgumentOutOfRangeException("milliseconds", milliseconds, ""); return new DateTimeOffset(milliseconds * 10000L + 621355968000000000L, TimeSpan.Zero); } public static long ToUnixTimeSeconds(this DateTimeOffset utcDateTime) { return utcDateTime.Ticks / 10000000L - 62135596800L; } public static long ToUnixTimeMilliseconds(this DateTimeOffset utcDateTime) { return utcDateTime.Ticks / 10000L - 62135596800000L; } [Test] public void UnixSeconds() { DateTime utcNow = DateTime.UtcNow; DateTimeOffset utcNowOffset = new DateTimeOffset(utcNow); long unixTimestampInSeconds = utcNowOffset.ToUnixTimeSeconds(); DateTimeOffset utcNowOffsetTest = UnixDateTime.FromUnixTimeSeconds(unixTimestampInSeconds); Assert.AreEqual(utcNowOffset.Year, utcNowOffsetTest.Year); Assert.AreEqual(utcNowOffset.Month, utcNowOffsetTest.Month); Assert.AreEqual(utcNowOffset.Date, utcNowOffsetTest.Date); Assert.AreEqual(utcNowOffset.Hour, utcNowOffsetTest.Hour); Assert.AreEqual(utcNowOffset.Minute, utcNowOffsetTest.Minute); Assert.AreEqual(utcNowOffset.Second, utcNowOffsetTest.Second); } [Test] public void UnixMilliseconds() { DateTime utcNow = DateTime.UtcNow; DateTimeOffset utcNowOffset = new DateTimeOffset(utcNow); long unixTimestampInMilliseconds = utcNowOffset.ToUnixTimeMilliseconds(); DateTimeOffset utcNowOffsetTest = UnixDateTime.FromUnixTimeMilliseconds(unixTimestampInMilliseconds); Assert.AreEqual(utcNowOffset.Year, utcNowOffsetTest.Year); Assert.AreEqual(utcNowOffset.Month, utcNowOffsetTest.Month); Assert.AreEqual(utcNowOffset.Date, utcNowOffsetTest.Date); Assert.AreEqual(utcNowOffset.Hour, utcNowOffsetTest.Hour); Assert.AreEqual(utcNowOffset.Minute, utcNowOffsetTest.Minute); Assert.AreEqual(utcNowOffset.Second, utcNowOffsetTest.Second); Assert.AreEqual(utcNowOffset.Millisecond, utcNowOffsetTest.Millisecond); } }