2017-12-19 12 views
1

Ich benutze eine Bibliothek, die die folgende Struktur verwendet, um einen Startzeitstempel wie folgt zu definieren.C++ benutzerdefinierte Zeit Datum Struktur zu utc Epoche

struct SYSTEMTIME { 
    /** year */ 
    WORD year; 

    /** month */ 
    WORD month; 

    /** day of week */ 
    WORD dayOfWeek; 

    /** day */ 
    WORD day; 

    /** hour */ 
    WORD hour; 

    /** minute */ 
    WORD minute; 

    /** second */ 
    WORD second; 

    /** milliseconds */ 
    WORD milliseconds; 
}; 

Für jeden Protokolleintrag nach dieser Zeit wird in Nanosekunden Unterschied von diesem ersten Zeitstempel angegeben.

Sagen wir seine UTC 2017-12-19 14:44:00 Und die ersten folgenden Protokolleinträge sind 397000ns danach.

Wie erstelle ich eine chronos, time_t oder unix Zeit von epoch aus der ersten SYSTEMTIME Struktur und dann fügen Sie die Nanosekunden hinzu.

Ausdruck sollte für diesen ersten Eintrag seines 2017.12.19 14: 44: 00,000397

Mit freundlichen Grüßen

+0

Ich würde in die andere Richtung gehen, wo ich mit einem Unix-Zeitstempel beginnen und es in Jahr konvertieren, Monat usw., falls erforderlich. Dies könnte ein wenig einfacher sein. – Detonar

+0

Leider ist das nicht möglich wegen der Bibliothek, die ich benutze. Also muss ich einen Unix-Timestamp erstellen, damit das funktioniert. –

Antwort

0

Aktualisiert

Ich habe den folgenden Code geringfügig geändert, um zwischen SYSTEMTIME und date::sys_time<std::chrono::milliseconds> statt date::sys_time<std::chrono::nanoseconds> zu konvertieren.

Begründung: Damit gibt es keinen impliziten Genauigkeitsverlust in to_SYSTEMTIME. Clients von to_SYSTEMTIME können die Genauigkeit explizit auf beliebige Weise abschneiden (floor, round, ceil usw.). Wenn die Genauigkeit nicht abgeschnitten wird (falls erforderlich), handelt es sich nicht um einen Laufzeitfehler.

Der Clientcode (in main) ist von dieser Änderung nicht betroffen.


Sie Howard Hinnant's free, open-source, header-only date/time library dafür verwenden könnte:

#include "date/date.h" 
#include <iostream> 

using WORD = int; 

struct SYSTEMTIME { 
    /** year */ 
    WORD year; 

    /** month */ 
    WORD month; 

    /** day of week */ 
    WORD dayOfWeek; 

    /** day */ 
    WORD day; 

    /** hour */ 
    WORD hour; 

    /** minute */ 
    WORD minute; 

    /** second */ 
    WORD second; 

    /** milliseconds */ 
    WORD milliseconds; 
}; 

date::sys_time<std::chrono::milliseconds> 
to_sys_time(SYSTEMTIME const& t) 
{ 
    using namespace std::chrono; 
    using namespace date; 
    return sys_days{year{t.year}/t.month/t.day} + hours{t.hour} + 
      minutes{t.minute} + seconds{t.second} + milliseconds{t.milliseconds}; 
} 

int 
main() 
{ 
    using namespace std::chrono; 
    using namespace date; 
    SYSTEMTIME st{2017, 12, 2, 19, 14, 44, 0, 0}; 
    auto t = to_sys_time(st) + 397000ns; 
    std::cout << floor<microseconds>(t) << '\n'; 
} 

Ausgang:

2017-12-19 14:44:00.000397 

Dieser wandelt eine SYSTEMTIME zu einem std::chrono::time_point<system_clock, milliseconds> (das ist eine Art-Alias ​​hat date::sys_time<milliseconds> genannt) durch die Sammel verschiedene Teile aus der SYSTEMTIME. Es fügt dann einfach nanoseconds zu dem time_point hinzu, schneidet es auf die gewünschte Genauigkeit von microseconds ab und streamt es aus.

Wenn sie nützlich wäre, ist hier, wie Sie die gleiche Bibliothek nutzen, um die entgegengesetzte Umwandlung zu tun:

SYSTEMTIME 
to_SYSTEMTIME(date::sys_time<std::chrono::milliseconds> const& t) 
{ 
    using namespace std::chrono; 
    using namespace date; 
    auto sd = floor<days>(t); 
    year_month_day ymd = sd; 
    auto tod = make_time(t - sd); 
    SYSTEMTIME x; 
    x.year = int{ymd.year()}; 
    x.month = unsigned{ymd.month()}; 
    x.dayOfWeek = unsigned{weekday{sd}}; 
    x.day = unsigned{ymd.day()}; 
    x.hour = tod.hours().count(); 
    x.minute = tod.minutes().count(); 
    x.second = tod.seconds().count(); 
    x.milliseconds = tod.subseconds().count(); 
    return x; 
} 
+0

Danke Howard, funktioniert wie ein Charme! –

0

Sie mktime() von <ctime> können tm zu konvertieren, zu time_t, die ein Integer-Typ ist .

tm ist sehr ähnlich zu Ihrem SYSTEMTIME struct. Daher könnten Sie sie leicht hin und her übersetzen können.

übersetzen Sie Ihre Struktur in tm und verwenden Sie dann gmtime() wie folgt.

#include <ctime> 

struct tm time = fromSystemtime(...); 
time_t timestamp; 

timestamp = mktime(&time); 

Weitere Einzelheiten finden Sie in den folgenden Links:

struct tm

time_t

mktime