現在、さまざまなプラットフォームがIANA タイム ゾーン データを解釈するかどうかを確認するために、一連のタイム ゾーン検証プログラムを作成しようとしています。
私が対象としている出力形式には、「英国夏時間」の「BST」や「太平洋標準時」の「PST」など、特定の時間に有効な略語が含まれています。
ほとんどのプラットフォームでは、これは簡単ですが、奇妙なことに、ICU4J は機能していないようです。SimpleDateFormat
ドキュメントによると、探しているものを取得するために「zzz」のパターンを使用できるはずですが、これは多くの場合、GMT+X の「O」パターンにフォールバックするようです。一部のタイム ゾーンでは、省略形がまったくありません。
ニューヨークを使用した短い例:
import java.util.Date;
import java.util.Locale;
import com.ibm.icu.util.TimeZone;
import com.ibm.icu.text.SimpleDateFormat;
public class Test {
public static void main(String[] args) {
TimeZone zone = TimeZone.getTimeZone("America/New_York");
SimpleDateFormat format = new SimpleDateFormat("zzz", Locale.US);
format.setTimeZone(zone);
// One month before the unix epoch
System.out.println(format.format(new Date(-2678400000L))); // GMT-5
// At the unix epoch
System.out.println(format.format(new Date(0L))); // EST
}
}
(私は ICU4J 55.1 を使用して実行しています。ストック ダウンロードと 2015e データ リリースで更新した後の両方です。)
ICU4J がその省略形を tz データから取得しているのか、CLDR から取得しているのかは明確ではありません。ここで違いを示唆する tz データに何もないことを考えると、後者であると思われます。
また、ロケールの影響も受けているようですが、これは妥当だと思います。米国のロケールを使用すると、アメリカ/ニューヨークの EST/EDT が表示されますが、ヨーロッパ/ロンドンの場合は何も表示されません。UKロケールでは、ヨーロッパ/ロンドンのGMT/BSTが表示されますが、アメリカ/ニューヨークの場合は何も表示されません:(
ICU4J を tz 略語に戻すよう説得する方法はありますか? 私の非常に具体的なケースでは、それが私が探しているすべてです。
アップデート
RealSkeptic のコメントのおかげで、TimeZoneNames
フォーマットせずにこのデータを取得するよりクリーンな方法のようです。それはすべてとても有望に聞こえます-さえありTimeZoneNames.getTZDBInstance
ます:
TimeZoneNames.NameType.SHORT_STANDARD
IANA tz データベースのゾーンの省略形と互換性がある (ローカライズされていない) 特定の短いゾーン名 (およびTimeZoneNames.NameType.SHORT_DAYLIGHT
)のみを含む TimeZoneNames のインスタンスを返します。
それは私が望んでいることとほぼ同じですが、ほとんどの場合、1970 年よりも前のものではなく、関連するすべてのデータが含まれているわけでもありません。
import static com.ibm.icu.text.TimeZoneNames.NameType.SHORT_STANDARD;
import com.ibm.icu.text.TimeZoneNames;
import com.ibm.icu.text.TimeZoneNames.NameType;
import com.ibm.icu.util.ULocale;
public class Test {
public static void main(String[] args) {
TimeZoneNames names = TimeZoneNames.getTZDBInstance(ULocale.ROOT);
long december1969 = -2678400000L;
// 24 hours into the Unix epoch...
long january1970 = 86400000L;
// null
System.out.println(
names.getDisplayName("America/New_York", SHORT_STANDARD, december1969));
// EST
System.out.println(
names.getDisplayName("America/New_York", SHORT_STANDARD, january1970));
// null
System.out.println(
names.getDisplayName("Europe/London", SHORT_STANDARD, december1969));
// null
System.out.println(
names.getDisplayName("Europe/London", NameType.SHORT_STANDARD, january1970));
}
}
この時点で間接的なことがほとんどないことを考えると - 私は ICU4J に私が望むものを正確に伝えています - 私の疑いは、情報が利用できないということです :(