I get human readable timestamps into my program. I want to store them in a database and work with them in different ways. I'd prefer to represent them as long ints since that is easier and more efficient but it's also handy to be able to flip between what's handy for a machine to read and what's handy for a human.
I've hacked together the following test program including functions to convert to and from human readable timestamps to longs and back again.
// g++ -o timetest timetest.cpp -std=c++11
#include <iostream>
#include <sstream>
#include <boost/date_time.hpp>
#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/date_time/posix_time/posix_time_io.hpp>
long millis_from_date(const std::string& s)
{
boost::posix_time::ptime pt;
std::istringstream is(s);
auto* f = new boost::posix_time::time_input_facet("%Y-%m-%dT%H:%M:%S.%FZ");
std::locale loc(std::locale(""), f);
is.imbue(loc);
is >> pt;
boost::posix_time::ptime timet_start(boost::gregorian::date(1970,1,1));
boost::posix_time::time_duration diff = pt - timet_start;
return diff.total_milliseconds();
}
std::string date_from_millis(long ms)
{
static const boost::posix_time::ptime epoch(boost::gregorian::date(1970,1,1));
boost::posix_time::time_facet * facet = new boost::posix_time::time_facet("%Y-%m-%dT%H:%M:%S.%fZ");
std::ostringstream stream;
stream.imbue(std::locale(stream.getloc(), facet));
stream << epoch + boost::posix_time::milliseconds(ms);;
return stream.str();
}
int main()
{
std::string time = "2016-04-14T07:47:50.120043Z";
std::cout << "Initial input: " << time << std::endl;
std::cout << std::endl;
{
long millis = millis_from_date(time);
std::cout << "Initial input in millis: " << millis << std::endl;
std::string newtime = date_from_millis(millis);
std::cout << "Converted back to date: " << newtime << std::endl;
}
{
long millis = millis_from_date(time);
std::cout << "Initial input in millis: " << millis << std::endl;
std::string newtime = date_from_millis(millis);
std::cout << "Converted back to date: " << newtime << std::endl;
}
return 0;
}
Here's the sample output.
Initial input: 2016-04-14T07:47:50.120043Z
Initial input in millis: 1460620070000
Converted back to date: 2016-04-14T07:47:50.000000Z
Initial input in millis: 1460620070000
Converted back to date: 2016-04-14T07:47:50.000000Z
As you can see, when converting to millis fractional second information is lost so what you get is seconds since begin of epoch with 000 tacked on the end.. Thus when converting the resulting long back to a human readable timestamp the fractional second information is lost.
I've tried quite a few things by now and I can't figure out how the millis_from_date function should work without losing the fractional second info. Any ideas???
Aucun commentaire:
Enregistrer un commentaire