Reputation: 143
I am developing a C++ application on Visual Studio in which I have a string that contains a datetime value and I must convert it into another string with the date and time in the format dd-mm-yyyy HH:MM:SS
For example, if the string sDateTime has the value "1643873040", I must get another string sDateAndTime with the value "02/03/2022, 08:24:00"
I have not found any tutorials or forums that explain how to do this conversion in a C or C++ program developed with Visual Studio and I would appreciate any help or suggestions.
Upvotes: 0
Views: 1748
Reputation: 47923
Your value 1643873040 appears to be a Unix time value. It's unusual to have it as a string, because it's obviously an integer. So the first thing to do is to convert it to an actual integer. The traditional type in C for this sort of thing is time_t
. (It used to be 32 bits, but these days it's usually 64 bits.)
#include <stdlib.h>
#include <stdio.h>
#include <time.h>
const char *sDateTime = "1643873040";
time_t t = strtoll(sDateTime, NULL, 10);
Next, to convert that number t
into a human-readable format, the first step is to use the function localtime
, which returns a pointer to a "broken down" time structure, struct tm
:
struct tm *tmp = localtime(&t);
Next, you can use the strftime
function to create a string from the struct tm
:
char strbuf[30];
strftime(strbuf, sizeof(strbuf), "%Y-%m-%d %H:%M:%S", tmp);
printf("%s\n", strbuf);
This prints:
2022-02-03 02:24:00
Or, you can print the fields from the struct tm
directly:
printf("%d-%02d-%02d %02d:%02d:%02d\n",
tmp->tm_year+1900, tmp->tm_mon+1, tmp->tm_mday,
tmp->tm_hour, tmp->tm_min, tmp->tm_sec);
Here, though, you have to be careful, because the tm_mon
field is 0-based, and tmp_year
is offset by 1900.
These are the ways I always do it, although it must be admitted that the localtime
function is problematic by modern standards, in that it returns a pointer to static data and is not therefore thread-safe. There's a thread-safe or "reentrant" version you can use instead:
struct tm tmbuf;
tmp = localtime_r(&t, &tmbuf);
(Or, as you've learned, there's a different alternative version, localtime_s
, although I'm not aware of any advantage it might have over localtime_r
.)
Finally, for completeness I might mention that there's also a simpler way, that goes straight from the time_t
value to a string, without any localtime
calls or a struct tm
at all:
printf("%s", ctime(&t));
This prints
Thu Feb 3 02:24:00 2022
but it's quite a bit less flexible, because there's no way to change it. ctime
's output format is fixed.
A time_t
value like 1643873040 usually represents UTC, also known as GMT. The localtime
function takes care of converting it to your local time zone (including DST corrections, if necessary). If you want UTC time instead, without applying time zone and DST corrections, you can call gmtime
instead of localtime
.
This answer has been for C. The localtime
, gmtime
, and strftime
functions will work fine in C++ also, although C++ has its own, perhaps preferred ways of doing it.
Upvotes: 2
Reputation: 143
I have modified the previous example, obtained based on your answers, so that now it works in VisualStudio:
uint64_t timeStamp = 0;
std::istringstream iss("1550267535");
iss >> timeStamp;
time_t localTime = timeStamp;
struct tm timeInfo;
localtime_s(&timeInfo, &localTime);
printf ("%d-%02d-%02d %02d:%02d:%02d",
1900 + timeInfo.tm_year, timeInfo.tm_mon, timeInfo.tm_mday,
timeInfo.tm_hour, timeInfo.tm_min, timeInfo.tm_sec);
Thanks a lot.
Upvotes: 0