以前より取り沙汰されてはいる、Java-Collectionのdouble-braceによる初期化について。
Map<String, String> mp = new HashMap<String, String>() {{ put("abc", "ABC"); put("def", "DEF"); put("ghi", "GHI"); }};
のようにインスタンス生成と初期化を行うコードはJava8以前にはちょいちょい見られ。
今もまぁちょいちょい使うのだけれど。
このdouble-braceによる初期化当初よりメモリリークが指摘され、注意が必要とされている。
匿名内部クラス(annonymous inner class)が生成され”強い外部参照”が作成されるためガーベージコレクションされることなく残り続けるというもので、繰り返し処理されるロジックでは避けるべきとされている。
(https://blog.p-y.wtf/avoid-java-double-brace-initialization で詳しく解説されている)
でもって、じゃぁ、というのはJava9以降なら簡単で、
Map<String, String> mp = Map.of("abc", "ABC", "def", "DEF", "ghi", "GHI"};
とするだけ。もちろんMap.ofの場合はImmutable Collection(不変コレクション)を返すので、putなどの編集・追加・削除操作はできないが、ごそっと初期化したい時ってぇのはImmutableで構わないケースがほとんどなので問題はないだろう。
ただ”ガーベージコレクションされない”が致命的でない場合は、double-braceも便利な書き方ではあるので、例えば単発Java Applicationのループ外での初期設定とかでは十分有効だといえる。
つーか、コレクションの初期化は面倒なのはわかるのだけれど他の言語では割と簡単にできるものであるし、ささっと初期化できないってのはなんだかなーとは思うわけだがまぁそういうものだししょうがない。