Odirection
Odirection

Reputation: 29

Converting epoch time to formatted GMT and back C++

I'm trying to convert epoch time to formatted GMT string and back. The first conversion is correct. I verified by https://www.epochconverter.com/

However, when I convert the formatted GMT back to epoch time, the result is incorrect at minute & second. The function get_time() seems to be correct but timegm() is not. Here is my code:

#include <string>
#include <iostream>
#include <iomanip>
#include <sstream>
#include <time.h>

void cvt_epoch2formatGmt(double ts, std::string& format){
    time_t timestamp = time_t(ts);

    char time_buf[80];
    struct tm gmt;
    gmt = *gmtime(&timestamp);
    strftime(time_buf, sizeof(time_buf), "%Y%m%d_%H%M%S", &gmt);
    format = time_buf;
}

double cvt_formatGmt2epoch(const std::string& formatted_ts){
    std::tm tm;
    std::stringstream ss(formatted_ts);
    ss >> std::get_time(&tm, "%Y%m%d_%H%M%S");
    double epoch = timegm(&tm);
    return epoch;
}

int main(){
    std::string format;
    double ts = 1671686472;
    cvt_epoch2formatGmt(ts, format);
    std::cout << format << std::endl;

    double epoch = cvt_formatGmt2epoch(format);
    std::cout << std::fixed << epoch << std::endl;
    if (std::abs(epoch-ts) > 1){
        std::cout << "wrong conversion" << std::endl;
        return 1;
    }

    return 0;
}

Updated: I made wrong at return type (float) of the function cvt_formatGmt2epoch(). It must be the double. I updated the code, and it works correct now

Upvotes: 2

Views: 384

Answers (1)

yeputons
yeputons

Reputation: 9238

float is not precise enough, so the result of timegm is rounded by returning from cvt_formatGmt2epoch. Use double as the return type.

Even better, use time_t, it's the return type of timegm and it's an integer so you avoid a myriad of other problems with floating-point numbers, year 2038, etc.

Upvotes: 2

Related Questions