¿Cómo se convierte el tiempo de época en C #?

¿Cómo se convierte el tiempo de época Unix en tiempo real en C #? (Época que comienza el 1/1/1970)

Supongo que te refieres al tiempo Unix , que se define como el número de segundos desde la medianoche (UTC) del 1 de enero de 1970.

public static DateTime FromUnixTime(long unixTime) { return epoch.AddSeconds(unixTime); } private static readonly DateTime epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); 

Con todo el mérito de LukeH, he reunido algunos métodos de extensión para facilitar su uso:

 public static DateTime FromUnixTime(this long unixTime) { var epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); return epoch.AddSeconds(unixTime); } public static long ToUnixTime(this DateTime date) { var epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); return Convert.ToInt64((date - epoch).TotalSeconds); } 

Tenga en cuenta el siguiente comentario de CodesInChaos que el anterior FromUnixTime devuelve un DateTime con un Kind de Utc , lo cual está bien, pero el ToUnixTime anterior es mucho más sospechoso en que no tiene en cuenta el tipo de DateTime la date dada. Para permitir que la Kind date sea Utc o Local , use ToUniversalTime :

 public static long ToUnixTime(this DateTime date) { var epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); return Convert.ToInt64((date.ToUniversalTime() - epoch).TotalSeconds); } 

ToUniversalTime convertirá un DateTime Local (o Unspecified ) en Utc .

si no desea crear la instancia de DateTime de época cuando pasa de DateTime a epoch, también puede hacer:

 public static long ToUnixTime(this DateTime date) { return (date.ToUniversalTime().Ticks - 621355968000000000) / 10000000; } 

La última versión de .Net (v4.6) acaba de agregar compatibilidad integrada para las conversiones de tiempo de Unix. Eso incluye el tiempo hacia y desde Unix representado por segundos o milisegundos.

  • Tiempo de Unix en segundos para DateTimeOffset :
 DateTimeOffset dateTimeOffset = DateTimeOffset.FromUnixTimeSeconds(1000); 
  • DateTimeOffset a tiempo Unix en segundos:
 long unixTimeStampInSeconds = dateTimeOffset.ToUnixTimeSeconds(); 
  • Tiempo de Unix en milisegundos a DateTimeOffset :
 DateTimeOffset dateTimeOffset = DateTimeOffset.FromUnixTimeMilliseconds(1000000); 
  • DateTimeOffset a tiempo Unix en milisegundos:
 long unixTimeStampInMilliseconds= dateTimeOffset.ToUnixTimeMilliseconds(); 

Nota: estos métodos se convierten desde y hacia DateTimeOffset . Para obtener una representación DateTime simplemente use la propiedad DateTimeOffset.DateTime :

 DateTime dateTime = dateTimeOffset.UtcDateTime; 

En realidad, desea agregar milisegundos (milisegundos), no segundos. Agregar segundos le dará una excepción fuera de rango.

 // convert datetime to unix epoch seconds public static long ToUnixTime(DateTime date) { var epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); return Convert.ToInt64((date.ToUniversalTime() - epoch).TotalSeconds); } 

Debería usar ToUniversalTime () para el objeto DateTime.

Utilizo los siguientes métodos de extensión para la conversión de época

 public static int GetEpochSeconds(this DateTime date) { TimeSpan t = DateTime.UtcNow - new DateTime(1970, 1, 1); return (int)t.TotalSeconds; } public static DateTime FromEpochSeconds(this DateTime date, long EpochSeconds) { var epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc); return epoch.AddSeconds(EpochSeconds); } 

Si quieres un mejor rendimiento, puedes usar esta versión.

 public const long UnixEpochTicks = 621355968000000000; public const long TicksPerMillisecond = 10000; public const long TicksPerSecond = TicksPerMillisecond * 1000; //[MethodImpl(MethodImplOptions.AggressiveInlining)] public static DateTime FromUnixTimestamp(this long unixTime) { return new DateTime(UnixEpochTicks + unixTime * TicksPerSecond); } 

Desde el punto de referencia rápido (BenchmarkDotNet) en net471 obtengo este número:

  Method | Mean | Error | StdDev | Scaled | -------------- |---------:|----------:|----------:|-------:| StackOverflow | 5.897 ns | 0.0897 ns | 0.0795 ns | 1.00 | MyCustom | 3.176 ns | 0.0573 ns | 0.0536 ns | 0.54 | 

2 veces más rápido contra la versión LukeH (si el rendimiento mater)

Esto es similar a cómo funciona DateTime internamente.

En caso de que necesite convertir una estructura timeval (segundos, microsegundos) que contenga UNIX time en DateTime sin perder precisión, así es como:

 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); } 

Si no está utilizando 4.6, esto puede ayudar Fuente: System.IdentityModel.Tokens

  ///  /// DateTime as UTV for UnixEpoch ///  public static readonly DateTime UnixEpoch = new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc); ///  /// Per JWT spec: /// Gets the number of seconds from 1970-01-01T0:0:0Z as measured in UTC until the desired date/time. ///  /// The DateTime to convert to seconds. /// if dateTimeUtc less than UnixEpoch, return 0 /// the number of seconds since Unix Epoch. public static long GetIntDate(DateTime datetime) { DateTime dateTimeUtc = datetime; if (datetime.Kind != DateTimeKind.Utc) { dateTimeUtc = datetime.ToUniversalTime(); } if (dateTimeUtc.ToUniversalTime() <= UnixEpoch) { return 0; } return (long)(dateTimeUtc - UnixEpoch).TotalSeconds; } 

Aquí está mi solución:

 public long GetTime() { DateTime dtCurTime = DateTime.Now.ToUniversalTime(); DateTime dtEpochStartTime = Convert.ToDateTime("1/1/1970 0:00:00 AM"); TimeSpan ts = dtCurTime.Subtract(dtEpochStartTime); double epochtime; epochtime = ((((((ts.Days * 24) + ts.Hours) * 60) + ts.Minutes) * 60) + ts.Seconds); return Convert.ToInt64(epochtime); }