.
This commit is contained in:
@@ -0,0 +1,52 @@
|
||||
|
||||
#pragma once
|
||||
|
||||
|
||||
#include <chrono>
|
||||
#include <string>
|
||||
#include <sstream>
|
||||
#include <cstdio>
|
||||
#include <ctime>
|
||||
|
||||
|
||||
namespace hos {
|
||||
namespace utils {
|
||||
|
||||
|
||||
/*
|
||||
* It took me way too long to come up with this solution (which I only consider as workaround,
|
||||
* but currently it seems to be the best solution).
|
||||
* There definitely needs to be much better support for timestamp-to-string conversion in C++,
|
||||
* the current situation is way too unsatisfying. And boost isn't much of a help either.
|
||||
*/
|
||||
template<class _CLOCK>
|
||||
std::string timestamp_to_ISO8601(const std::chrono::time_point<_CLOCK>& timestamp) {
|
||||
std::stringstream ss;
|
||||
std::tm tm_time;
|
||||
char temp[256];
|
||||
// First convert timestamp to time_t (loosing precision)
|
||||
std::time_t time = std::chrono::system_clock::to_time_t(timestamp);
|
||||
// Then convert time_t to tm_time
|
||||
localtime_r(&time, &tm_time);
|
||||
// Print first part of ISO8601 string
|
||||
std::strftime(temp, sizeof(temp), "%FT%H:%M:", &tm_time);
|
||||
ss << temp;
|
||||
// Get lost precision by converting out time_t back to a timestamp and substracting it from our given timestamp,
|
||||
// and add seconds to avoid the "0.xyz" problem
|
||||
std::chrono::duration<double> msecs = timestamp - std::chrono::system_clock::from_time_t(time) + std::chrono::seconds(tm_time.tm_sec);
|
||||
// Print seconds part of ISO8601 string
|
||||
std::snprintf(temp, sizeof(temp), "%09.6f", msecs.count()); // is more compact than C++ counterpart
|
||||
std::string secpart(temp);
|
||||
std::replace(secpart.begin(), secpart.end(), '.', ',' ); // ISO 8601 prefers ',' over '.' as decimal mark.
|
||||
ss << secpart;
|
||||
// Get and print timezone part of ISO8601 string
|
||||
std::strftime(temp, sizeof(temp), "%z", &tm_time);
|
||||
ss << temp;
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
|
||||
|
||||
} // namespace libvariant
|
||||
} // namespace hos
|
||||
|
||||
Reference in New Issue
Block a user