我目前正在使用java.util.TimeZone在不同的时区工作。
我要做的第一件事是使用TimeZone.getAvailableIDs();获取TimeZone ID列表

它返回了一堆Etc/GMT ID,例如

Etc/GMT
Etc/GMT+0
Etc/GMT+1


Javadoc for TimeZone说使用“例如,GMT+10GMT+0010

为了确保我使用的是正确的,我用两个ID进行了一次小测试,结果与我期望的不符:

String id = "GMT-1";
Calendar c = Calendar.getInstance(TimeZone.getTimeZone(id));
System.out.println(id + '\n' + c.getTimeZone().getDisplayName() + " HOUR_OF_DAY " + c.get(Calendar.HOUR_OF_DAY) + '\n');

id = "GMT+1";
c = Calendar.getInstance(TimeZone.getTimeZone(id));
System.out.println(id + '\n' + c.getTimeZone().getDisplayName() + " HOUR_OF_DAY " + c.get(Calendar.HOUR_OF_DAY) + '\n');

id = "Etc/GMT-1";
c = Calendar.getInstance(TimeZone.getTimeZone(id));
System.out.println(id + '\n' + c.getTimeZone().getDisplayName() + " HOUR_OF_DAY " + c.get(Calendar.HOUR_OF_DAY) + '\n');

id = "Etc/GMT+1";
c = Calendar.getInstance(TimeZone.getTimeZone(id));
System.out.println(id + '\n' + c.getTimeZone().getDisplayName() + " HOUR_OF_DAY " + c.get(Calendar.HOUR_OF_DAY) + '\n');


显示输出

GMT-1
GMT-01:00 HOUR_OF_DAY 18

GMT+1
GMT+01:00 HOUR_OF_DAY 20

Etc/GMT-1
GMT+01:00 HOUR_OF_DAY 20

Etc/GMT+1
GMT-01:00 HOUR_OF_DAY 18


所以我的问题是:这些Etc/GMT ID是做什么用的?为什么当我使用+ X时他们会给我-X,反之亦然?

最佳答案

Etc/GMT...时区主要是为了与POSIX标准向后兼容,后者指定了GMT以西的正偏移量,而不是您可能习惯的GMT以东的典型约定。

在大多数情况下,您不应使用它们。例如,如果您位于美国太平洋时区,则应使用标识符America/Los_Angeles。它在冬季的标准时间为UTC-8,在夏季的白天为UTC-7。您不应该只使用Etc/GMT+8,因为这不会考虑夏令时。

除了向后兼容之外,这些固定偏移区域起作用的另一个区域是出于航海目的。海上船只对时间的设置有很多控制权,但通常使用固定的偏移量(经度间隔15度)。对于大西洋中的船舶,使用时区设置标识符Etc/GMT+3是完全可以接受的。

只是不要忘记将符号反转。 Etc/GMT+3 = UTC-3

补充阅读:


The comments in the etcetera file of the IANA/Olson time zone data
The timezone tag wiki
Wikipedia article on Nautical Time

10-07 13:19
查看更多