S-JIS[2026-09-16]
Java27のLazy Constants(プレビュー版)について。
2026/3/18にリリースされたJava26で、プレビュー版としてLazyConstantが新設された。
2026/9/15にリリースされたJava27では、LazyConstantのisInitialized()とorElse()が削除された。
LazyConstantは、遅延初期化する定数を定義できるインターフェース。
(RustのOnceLock相当)
常に使うとは限らない定数で初期化処理が重い場合は、初期化を遅延させたいことがある。
つまり、その定数を持つクラスやインスタンスが生成された時点では初期化を行わず、初めて使うときに一度だけ初期化して、後はその値を使い回す。
そのような場合にLazyConstantは便利。
Javaの定数は、その定数を持つクラスやインスタンスが生成されるときに初期化される。
private static final String CONSTANT = "value"; // 初期化
public static String getConstant() {
return CONSTANT;
}
private static final String CONSTANT;
static {
CONSTANT = "value"; // 初期化
}
public static String getConstant() {
return CONSTANT;
}
が、初めて使うときに初期化したい場合は、finalを外し、ゲッターメソッド内で初期化を行う。
private static String CONSTANT; // 初期値はnull
public static String getConstant() {
if (CONSTANT == null) {
CONSTANT = "value"; // 初期化
}
return CONSTANT;
}
ただ、この方法は、スレッドセーフにしようとすると(マルチスレッドで同時に呼ばれても(効率よく)一度のみ初期化するのは)意外と面倒だったりする。
また、finalが付いていた方がJavaによる最適化の手助けになるらしい。
そこでLazyConstantを使い、以下のように書くことが出来る。
private static final LazyConstant<String> CONSTANT = LazyConstant.of(() -> "value"); // 初期化
public static String getConstant() {
return CONSTANT.get();
}
LazyConstantはJava27ではプレビュー版の機能なので、この機能を使いたい場合はコンパイル時にjavacコマンドに--enable-previewを付ける必要があり、
また、実行時にjavaコマンドに--enable-previewを付ける必要がある。
JShellで試す場合もjshellコマンドに--enable-previewを付ける。
> javac --enable-preview --release 27 Example.java > java --enable-preview Example
> java --enable-preview Example.java
| メソッド | 説明 | 例 |
|---|---|---|
LazyConstant<T> of(Supplier<T> computingFunction) |
値の初期化用のSupplierを指定してLazyConstantオブジェクトを生成する。 | static final LazyConstant<String> CONSTANT = LazyConstant.of(()->"value"); |
| メソッド | 説明 | 例 |
|---|---|---|
T get() |
値を取得する。 値が初期化されていない場合は初期化される。 |
String s = CONSTANT.get(); |