Open TomGarden opened 1 year ago
#include "date/tz.h"
#include <chrono>
#include <iostream>
#include <sstream>
int
main()
{
using namespace date;
using namespace std;
using namespace std::chrono;
string input{"2022-12-13 10:32:06"};
cout << input << '\n';
istringstream in{std::move(input)};
in.exceptions(ios::failbit);
local_seconds ltp;
in >> parse("%F %T", ltp);
auto utp = locate_zone("Asia/Shanghai")->to_sys(ltp);
string output = format("%F %T", utp);
cout << output << '\n';
}
In a nutshell, the input is local_time
. And one can use the time_zone
"Asia/Shanghai" to transform it into sys_time
(which is a close approximation to UTC). Then you can format the sys_time
however you want.
This program outputs:
2022-12-13 10:32:06
2022-12-13 02:32:06
An alternative to:
auto utp = locate_zone("Asia/Shanghai")->to_sys(ltp);
is:
auto utp = zoned_time{"Asia/Shanghai", ltp}.get_sys_time();
They are both equivalent. zoned_time
is just a pair of {time_zone*, time point}
. The zoned_time
constructor calls locate_zone
and to_sys
for you. In this example, one is about as good as the other. In other examples direct use of the time_zone
is simpler, or the use of zoned_time
is simpler. In the end, zoned_time
is a simple wrapper around {time_zone*, time point}
to enable some higher-level code to have simpler syntax.
A key point to observe in this example is that the input is parsed into a local_time
type. This detail is what enables the type-safe transformation of the local time in "Asia/Shanghai" to sys_time
.
In the event that the "other time zone" is not UTC, for example "America/New_York", then the use of zoned_time
makes the syntax simpler:
local_seconds ltp;
in >> parse("%F %T", ltp);
auto Stp = zoned_time{"Asia/Shanghai", ltp};
auto Ntp = zoned_time{"America/New_York", Stp};
string output = format("%F %T", Ntp);
Output:
2022-12-13 10:32:06
2022-12-12 21:32:06
One can construct one zoned_time
from another and the invariant is that the two zoned_time
s will point to the same UTC time_point
.
One could do this at the time_zone
level, but the syntax would be slightly messier.
local_seconds ltp;
in >> parse("%F %T", ltp);
auto utp = locate_zone("Asia/Shanghai")->to_sys(ltp);
auto Ntp = locate_zone("America/New_York")->to_local(utp);
string output = format("%F %T", Ntp);