Open shawncao opened 9 months ago
this is my hack to work around this issue, not ideal:
static int64_t time(const std::string_view datetime, const std::string& pattern) {
// introduce a special tag to handle iso8601 flexible values: DATE or DATETIME
// for example 2021-11-02, 2021-11-02T12:00:00Z, 2021-11-02T12:00:00.123Z
auto p = pattern;
if (pattern == "iso8601") {
if (datetime.size() == 10) {
p = "%F";
} else {
p = "%FT%TZ";
}
}
date::sys_time<std::chrono::microseconds> tp;
std::istringstream value(datetime.data());
value >> date::parse(p, tp);
if (value.fail()) {
LOG(ERROR) << "Failed to parse time: " << datetime;
return 0;
}
return seconds(tp);
}
What do you think about this?
// parse "%F" or "%FT%TZ"
int64_t
time(const std::string_view datetime)
{
std::istringstream in{datetime.data()};
date::sys_seconds tp;
std::chrono::seconds tod{};
in >> date::parse("%F", tp);
if (in.fail())
{
std::cerr << "Failed to parse time: " << datetime;
return 0;
}
in >> date::parse("T%TZ", tod);
tp += tod;
return tp.time_since_epoch().count();
}
The one thing it might not do right for you is interpret "2021-11-23T20:55:52" as equivalent to "2021-11-23" because of the syntax error in the time part (missing trailing Z). If you want to interpret syntax errors in an attempted time-of-day you could peek into the stream looking for 'T' and then commit to parsing a duration or returning an error.
This is pretty smart! Using two steps instead of one, thanks for sharing this!
@HowardHinnant may I ask you another question?
What is the name for a date time string like this "2023-09-17 17:08:00.368787+00:00", is this another standard? What pattern format to use to parse date time string like this?
Not sure about a standard name. But this will parse it:
#include "date/date.h"
#include <chrono>
#include <iostream>
#include <sstream>
int
main()
{
using namespace date;
using namespace std;
using namespace chrono;
istringstream in{"2023-09-17 17:08:00.368787+00:00"};
sys_time<microseconds> tp;
in >> parse("%F %T%Ez", tp);
cout << tp << '\n';
}
Awesome, thank you again!
I'm wondering if there is a flexible way to write the pattern so that it can parse either DATE or DATE-TIME (ISO8601)
for example, I have mixed values from a set:
I hope we can do
Obviously "%FT%T" will translate "2021-11-02" into value 0
Any ideas?