Note that tm
's member denoting the smallest time increment is tm_sec
, which is an int
which is defined only over the range:
Seconds after the minute [0,60] since C++11
So you won't be able to store a fraction of a second in a tm
, you'll just need to discard the number following the decimal place.
As suggested by Karsten Koop you can just read the year twice, the second %Y
will stomp the first:
auto fmt = "%H:%M:%S.%Y %Z %b %d %Y";
Live Example
That said, I'd recommend against using strptime
it is a POSIX function, using a standard function like get_time
would be preferable. This has one minor drawback; get_time
doesn't have knowledge of time zones, but then neither does tm
, with the exception of tm_isdst
which is the:
Daylight Saving Time flag. The value is positive if DST is in effect, zero if not and negative if no information is available
So you may have to assign tm_isdst
independently if you persue something like this:
tm tmbuf;
stringstream str("20:48:01.469 UTC MAR 31 2016");
str >> get_time(&tmbuf, "%H:%M:%S.%Y UTC %b %d %Y");
Live Example
My get_time
answer was a little hypocritical, cause while I speak of the importance of standardization I could only get it to run on libc++. As such I thought I'd post a more universal solution, which will also discard the time zone, so again you'll need to set tm_isdst
independently:
tm tmbuf{};
stringstream str("20:48:01.469 UTC MAR 31 2016");
string tm_mon;
str >> get_time(&tmbuf, "%T");
str.ignore(std::numeric_limits<std::streamsize>::max(), 'C');
str >> tm_mon >> get_time(&tmbuf, "%d %Y");
for (const auto& i : { "JAN"s, "FEB"s, "MAR"s, "APR"s, "MAY"s, "JUN"s, "JUL"s, "AUG"s, "SEP"s, "OCT"s, "NOV"s, "DEC"s }) {
if (equal(cbegin(tm_mon), cend(tm_mon), cbegin(i), cend(i), [](const unsigned char a, const unsigned char b) { return toupper(a) == b; })) break;
++tmbuf.tm_mon;
}
Live Example
This has 2 key dependencies:
- That the timezone always ends in the character
'C'
(it must be uppercase)
- That the month abbreviations fed in match one of those in my
initializer_list