我写了一个为任何日期提供夏令时信息的功能。但它仅适用于当地时区。
使用夏令时信息我的意思是:
功能是:
enum DST { DST_OFF, DST_ON, DST_OFFTOON, DST_ONTOOFF };
DST getdstinfo(int year, int month, int day) {
tm a = {};
a.tm_isdst = -1;
a.tm_mday = day;
a.tm_mon = month - 1;
a.tm_year = year - 1900;
tm b = a;
a.tm_hour = 23;
a.tm_min = 59;
mktime(&a);
mktime(&b);
if (a.tm_isdst && b.tm_isdst) return DST_ON;
else if (!a.tm_isdst && !b.tm_isdst) return DST_OFF;
else if (a.tm_isdst && !b.tm_isdst) return DST_OFFTOON;
else return DST_ONTOOFF;
}
如果我没有明确设置时区,这个功能似乎适用于Windows上的测试用例(Visual Studio 2010)。测试用例是:
#include <cstdlib>
#include <cstdio>
#include <ctime>
const char* WHAT[] = {
"noDST", "DST", "switch noDST to DST", "switch DST to noDST"
};
int main() {
const int DAY[][4] = {
{ 2012, 3, 24, DST_OFF },
{ 2012, 3, 25, DST_OFFTOON },
{ 2012, 3, 26, DST_ON },
{ 2012, 5, 22, DST_ON },
{ 2012, 10, 27, DST_ON },
{ 2012, 10, 28, DST_ONTOOFF },
{ 2012, 10, 29, DST_OFF },
{ 2013, 3, 30, DST_OFF },
{ 2013, 3, 31, DST_OFFTOON },
{ 2013, 4, 1, DST_ON },
{ 2013, 10, 26, DST_ON },
{ 2013, 10, 27, DST_ONTOOFF },
{ 2013, 10, 28, DST_OFF },
};
const int DAYSZ = sizeof(DAY) / sizeof (*DAY);
//_putenv("TZ=Europe/Berlin");
//_tzset();
for (int i = 0; i < DAYSZ; i++) {
printf("%04d.%02d.%02d (%-20s) = %s\n",
DAY[i][0], DAY[i][1], DAY[i][2],
WHAT[DAY[i][3]],
WHAT[getdstinfo(DAY[i][0], DAY[i][1], DAY[i][2])]);
}
return 0;
}
结果是:
2012.03.24 (noDST ) = noDST
2012.03.25 (switch noDST to DST ) = switch noDST to DST
2012.03.26 (DST ) = DST
2012.05.22 (DST ) = DST
2012.10.27 (DST ) = DST
2012.10.28 (switch DST to noDST ) = switch DST to noDST
2012.10.29 (noDST ) = noDST
2013.03.30 (noDST ) = noDST
2013.03.31 (switch noDST to DST ) = switch noDST to DST
2013.04.01 (DST ) = DST
2013.10.26 (DST ) = DST
2013.10.27 (switch DST to noDST ) = switch DST to noDST
2013.10.28 (noDST ) = noDST
但如果我取消注释行_putenv
和_tzset
,我会得到每个测试用例的结果DST
(可能是因为我们现在有DST)。
_putenv
和_tzset
后的正确结果?