現在にタイムリープしたJava8エンジニアに今のJavaを説明するときに見せるページ
これはなに
kaseitako.icon 何が大きな変更とするかは完全に主観で決めとります
kaseitako.icon 全然網羅もしてないと思う、ごめん
背景
kaseitako.icon は以前Kotlinエンジニアだったが、Javaの知識は8か11あたりで止まっている 趣味で久しぶりに今のJavaを書こうかなと思い、知った内容をまとめておくと嬉しいこともあるかなと思った 内容
(バージョン順に書いていく) kaseitako.icon バージョン間違ってたらごめんね
module-info.java java9
src/main/java直下に module com.example.myapp { で始まるファイルを置いて依存関係を定義できる
kaseitako.icon 普通の開発じゃ使わなさそう
jshell java9
CLIでコード動かせるやつ
code:java
vscode ➜ / $ jshell
jshell> LocalDate.now()
$1 ==> 2026-01-24
jshell> /exit
| Goodbye
コレクションを of で不変リストとして初期化できる java9
List.of() Set.of() Map.of()
kaseitako.icon Javaの new List<*> とかはミュータブルです(再確認)
ローカル変数型推論 (var) java10
変数宣言に var が使える
var map = Map.of("key", "value");
String API に機能追加 java11 java15
code:java
" ".isBlank(); // true
"Hello\nWorld".lines().forEach(System.out::println);
"Java".repeat(3); // "JavaJavaJava"
Java15では formatted() も追加されたらしい
code:java
String message = "こんにちは、%sさん!あなたは%d歳です。".formatted(name, age);
switchでアローが使える java14
code:java
switch (dayOfWeek) {
case MONDAY, THURSDAY, FRIDAY -> WorkStyle.GO_TO_OFFICE;
case TUESDAY, WEDNESDAY -> WorkStyle.WORK_FROM_HOME;
case SATURDAY, SUNDAY -> WorkStyle.HOLIDAY;
};
上記のように書ける。従来の記法と違い以下のメリットがある
case にカンマ区切りで複数条件指定できる
fall through(break を忘れると下のcaseも処理されてしまう)が起きない
switch式 java14
switchの結果をそのまま受け取れる
kaseitako.icon 君が好きだ
code:java
WorkStyle workStyle = switch (dayOfWeek) { ... };
テキストブロック
待望の機能
kaseitako.icon もう少し早くリリースされていれば助かった命もありそう
code:java
String html = """
<html>
<body>
<p>Hello</p>
</body>
</html>
""";
インデントは終了デリミタ """ の位置が基準になる。上の例で言うと <html /> の左にスペースはない
kaseitako.icon 変数を埋め込む機能とかは残念ながらないらしいので formatted() で頑張ってくださいらしい
instanceof パターンマッチング java16
code:java
if (obj instanceof String s) {
System.out.println(s.length()); // sは自動的にString型
}
kaseitako.icon Kotlin で言うスマートキャストっぽいやつ
record java16
code:java
public record Person(String name, int age) {
public Person { // コンストラクタ定義は任意
if (age < 0) throw new IllegalArgumentException("年齢は0以上");
name = name.trim();
}
}
上記で プロパティと同名のゲッター equals() hashCode() toString() が勝手に生えてくる
kaseitako.icon Kotlin の data class に似ているが、セッターがないのでnewした後に二度と値を変更できない
kaseitako.icon 追記できるコンストラクタの値はプロパティではなく、コンストラクタ引数を操作しているらしいっす
Sealed Classes java17
継承先を制限できる
code:java
// 継承先をCircle、Rectangle、Triangleに限定
public sealed class Shape permits Circle, Rectangle, Triangle {
public abstract double area();
}
public final class Circle extends Shape {
private final double radius;
public Circle(double radius) { this.radius = radius; }
public double area() { return Math.PI * radius * radius; }
}
// non-sealedで継承を再開放することも可能
public non-sealed class Triangle extends Shape { /* ... */ }
RandomGenerator java17
code:java
RandomGenerator rng = RandomGenerator.of("Xoshiro256PlusPlus");
rng.ints(10, 0, 100).forEach(System.out::println);
Pattern Matching for switch java21
switchのパターンマッチが強化された
kaseitako.icon 調べると以下などは特に便利な変更に感じた
レコードクラスの指定許可
Sealedクラスが指定可能
caseに「when」で条件を追加可能
code:java
// 例:when句によるガード条件
static String describe(Object obj) {
return switch (obj) {
case String s when s.length() > 10 -> "長い文字列";
case String s -> "短い文字列";
default -> "その他";
};
}
Sequenced Collections(順序付きコレクションの統一API) java21
kaseitako.icon めんどいのでAIくんの説明を抜粋
従来、List・Deque・LinkedHashSetで異なっていた「最初/最後の要素アクセス」がSequencedCollectionインターフェースで統一された。
code:java
// 新しい統一API
SequencedCollection<String> seq = new ArrayList<>(List.of("a", "b", "c"));
String first = seq.getFirst(); // "a"
String last = seq.getLast(); // "c"
seq.addFirst("z"); // 先頭に追加
seq.addLast("end"); // 末尾に追加
// 逆順ビュー
for (String s : seq.reversed()) {
System.out.println(s); // end, c, b, a, z
}
// SequencedMapも同様
SequencedMap<String, Integer> map = new LinkedHashMap<>();
map.put("Apple", 10);
map.put("Banana", 20);
map.putFirst("Cherry", 30); // 先頭に追加
Entry<String, Integer> first = map.firstEntry(); // Cherry=30
java.lang.IO java25
System.out.println() ではなく IO.println() で出力できるようになった
Mainメソッドを書くのが楽ちんに java25
code:java
void main() {
IO.println("Hello Java!");
}
kaseitako.icon すげえ