Reputation: 59
I want a soultion in C++ to get hours diffreence between GMT time and any time zone. e.g. This is in Java I want to make in C++
// New York
Calendar c = new GregorianCalendar(TimeZone.getTimeZone("America/New_York"));
// Alaska
c = new GregorianCalendar(TimeZone.getTimeZone("America/Anchorage"));
// Difference between New York and Alaska
Please tell me how I can get this time zone in C++
Upvotes: 0
Views: 612
Reputation: 218750
I've been staring at Greg's good answer for a few days now, and am contemplating adding some syntax sugar to my timezone library:
namespace date
{
class zoneverter
{
const Zone* zp1_;
const Zone* zp2_;
public:
zoneverter(const Zone* z1, const Zone* z2)
: zp1_(z1)
, zp2_(z2)
{}
zoneverter(const Zone* z1, const std::string& z2)
: zoneverter(z1, locate_zone(z2))
{}
zoneverter(const std::string& z1, const Zone* z2)
: zoneverter(locate_zone(z1), z2)
{}
zoneverter(const std::string& z1, const std::string& z2)
: zoneverter(locate_zone(z1), locate_zone(z2))
{}
template <class Rep, class Period>
auto
operator<<(std::chrono::time_point<std::chrono::system_clock,
std::chrono::duration<Rep, Period>> tp) const
{
return zp1_->to_local(zp2_->to_sys(tp)).first;
}
};
} // namespace date
This adds a "streaming-like-object" which allows one to stream a std::chrono::time_point
through it to convert it from one timezone to another. It is a very simple device, which does nothing but add some syntax sugar, at the expense of dropping some information, from my timezone library.
It would be used like this:
int
main()
{
// So things don't get overly verbose
using namespace date;
using namespace std::chrono;
// Set up the zone converters:
zoneverter nyc_from_utc{"America/New_York", "UTC"};
zoneverter anc_from_nyc{"America/Anchorage", "America/New_York"};
// Get the current time in New York and convert that to the current time in Anchorage
auto now_nyc = nyc_from_utc << system_clock::now();
auto now_anc = anc_from_nyc << now_nyc;
// Output the difference
std::cout << make_time(now_nyc - now_anc) << '\n';
}
This currently outputs for me:
04:00:00.000000
I'm also unsure if this syntax sugar is sufficiently better than the current syntax to warrant its existence:
int
main()
{
// So things don't get overly verbose
using namespace date;
using namespace std::chrono;
// Set up the zones:
auto nyc_zone = locate_zone("America/New_York");
auto anc_zone = locate_zone("America/Anchorage");
// Get the current time in New York and the current time in Anchorage
auto now_utc = system_clock::now();
auto now_nyc = nyc_zone->to_local(now_utc).first;
auto now_anc = anc_zone->to_local(now_utc).first;
// Output the difference
std::cout << make_time(now_nyc - now_anc) << '\n';
}
Upvotes: 1
Reputation: 96
You can use the cctz library to calculate the difference in UTC offset between two different time zones at some specific time.
#include <chrono>
#include "cctz.h"
using namespace std::chrono;
cctz::TimeZone nyc;
cctz::LoadTimeZone("America/New_York", &nyc);
cctz::TimeZone anc;
cctz::LoadTimeZone("America/Anchorage", &anc);
const auto now = system_clock::now();
const auto nyc_off = cctz::BreakTime(now, nyc).offset;
const auto anc_off = cctz::BreakTime(now, anc).offset;
const auto off_diff = nyc_off - anc_off;
Now, the truth is that you really don't want to do that. Really. Healthy, modern code should never (did I say never, because I meant never) care about UTC offsets. Computing with UTC offsets is the job of your time zone library, and if your time zone library doesn't handle that for you, then you're using the wrong time zone library. If you think you care about UTC offsets, then I encourage you to look into the following:
[Disclaimer: I'm an author of cctz.]
Upvotes: 2