Javaの13明日リリース、最新かつ最も新しい機能の解釈

2017年8月には、半年に一度は、新しいリリースサイクルは厳密に時間のポイントを追跡するためのJavaリリース頻度のJCP執行委員会は、9月と各年の3月にリリースされます。

現在、JDKの公式サイトはすでにJDK 13進捗状況を確認することができ、JDK 13の最新バージョンは、2019年9月17日にリリースされます。

現在、リリース候補フェーズ(リリース候補の段階)でJDK13、9月17日にリリースされます。現在、このリリースに含まれるすべての固定されている、主に以下の5つが含まれています。

JEP 350、動的CDSアーカイブ

JEP 351、ZGC:Uncommit未使用のメモリー

JEP 353、レガシーソケットAPIを再実装

JEP 354:スイッチ式(プレビュー)

JEP 355、テキストブロック(プレビュー)

さんが一つずつこれらの5つの重要な機能をご紹介しましょう。

ダイナミックCDSアーカイブ

この機能はJEP310である:拡張に基づいてアプリケーションクラス・データの共有くる、CDSの動的CDSアーカイブはクラスデータ共有を指します。

だから、このJEP310はGeshaものでしょうか?

私たちは、あなたが同じ物理マシン/仮想マシン上で複数のJVMを起動するときに、各仮想マシンは、彼らは別の、メモリ使用量と起動コストが比較的高い必要があるすべてのクラスをロードすることを知っています。だから、Javaのチームは、各JVM間で共有いくつかのコアクラスによってCDSの概念を導入し、各JVMが唯一の独自のアプリケーションクラスをロードする必要があり、開始時間を低減し、他のコアクラスが共有されているので、JVMのメモリフットプリント減少しました。

CDSは、唯一のロードアプリケーションクラスローダクラスローダまたは自己定義されたクラスに基づいて行動することはできませんブートクラスローダロードしたクラスに基づいて行動することができます。

Javaの10では、CDSは、名前が示すように、また働くことができるブートクラスローダ、アプリケーションクラスローダとカスタムクラスローダに作用することができる以上のものをAppCDS、AppCDSに延長され、大幅にCDSの適用範囲を増加させました。また、それはカスタムクラスの開発は、共有、複数のJVMにロードすることができると述べました。

Javaの10は、メモリフットプリントを削減するために、異なるJavaプロセス全体でカテゴリ別にJEP310の共通のメタデータを含んでおり、起動時間を改善します。

しかし、JEP310使用AppCDSプロセスは非常に複雑であり、3つの手順が必要です。

1、决定要 Dump 哪些 Class
2、将类的内存 Dump 到归档文件中
3、使用 Dump 出来的归档文件加快应用启动速度
复制代码

今回は13 JEP 350でJDK、JEP310に基づいて、だけでなく、いくつかの拡張を行いました。Javaアプリケーションは、動的アーカイブクラスの実行を終了したことができ、クラスアーカイブは、アーカイブが存在しない場合、デフォルトのベース層のCDS(クラスデータ共有)をロードされたすべてのアプリケーションクラスとクラスライブラリを含むであろう。

言い換えれば、Javaの13で再利用AppCDSは時間に、それほど複雑では必要ありません。

ZGC:Uncommit未使用のメモリー

この問題を議論する前に、質問をお願いしたいと思い、JVMのGCメモリがオペレーティングシステムに解放されるのですか?

メモリは、GC処分した後、実際には、ガベージコレクタに依存する方法。バックOSのメモリは、JVMのヒープサイズを調整するためのものなので、このプロセスは、比較的リソースを消費しています。

でJDK 11では、Javaは、これはスケーラブルで、低遅延のガベージコレクタで、ZGCを導入しましたが、唯一の実験でした。そして、ZGC解放されたメモリは、オペレーティングシステムに返されません。

Javaの13で、JEP 351 ZGCは再びこのZGCは、ヒープメモリがオペレーティングシステムに返される使用することはできません強化ありません。現在、多くのシーンがメモリ内に存在するため、この機能の導入は、比較的高価なリソースは次の場合には、ある理由は、バックオペレーティングシステムにメモリがまだ非常に必要です:

  • コンテナの使用のためにお金を払う必要とする人によると1、
  • 2は、アプリケーションが長い時間アイドルと資源や環境のために競合する他の多くのアプリケーションと共有されることがあります。
  • 3、アプリケーションの実行中に非常に異なるヒープ領域の要件を有することができます。例えば、スタックの起動に必要な期間は、後に定常状態で実行スタック中に必要とされるよりも大きくてもよいです。

レガシーソケットAPIを再実装

保守が容易で、デバッグ、よりシンプルで現代的な実装がにjava.net.Socketおよびjava.net.ServerSocketのAPIを置き換える使用してください。

java.net.Socketは非常に古いjava.net.ServerSocketを達成し、JEPは、彼らが現代の実装を紹介しています。現代のデフォルトのJava実装では、13で達成されていますが、古い実装では、システムプロパティjdk.net.usePlainSocketImplを設定することで、それらを使用することができ、削除されません。

ソケットおよびServerSocketクラスの1つのインスタンスを実行するには、デバッグ出力を表示します。これがデフォルト(新しい)です。

java -XX:+TraceClassLoading JEP353  | grep Socket
[0.033s][info   ][class,load] java.net.Socket source: jrt:/java.base
[0.035s][info   ][class,load] java.net.SocketOptions source: jrt:/java.base
[0.035s][info   ][class,load] java.net.SocketImpl source: jrt:/java.base
[0.039s][info   ][class,load] java.net.SocketImpl$$Lambda$1/0x0000000800b50840 source: java.net.SocketImpl
[0.042s][info   ][class,load] sun.net.PlatformSocketImpl source: jrt:/java.base
[0.042s][info   ][class,load] sun.nio.ch.NioSocketImpl source: jrt:/java.base
[0.043s][info   ][class,load] sun.nio.ch.SocketDispatcher source: jrt:/java.base
[0.044s][info   ][class,load] java.net.DelegatingSocketImpl source: jrt:/java.base
[0.044s][info   ][class,load] java.net.SocksSocketImpl source: jrt:/java.base
[0.044s][info   ][class,load] java.net.ServerSocket source: jrt:/java.base
[0.045s][info   ][class,load] jdk.internal.access.JavaNetSocketAccess source: jrt:/java.base
[0.045s][info   ][class,load] java.net.ServerSocket$1 source: jrt:/java.base
复制代码

上記sun.nio.ch.NioSocketImpl出力は、新たなオファーの実現です。

あなたは、古い実装を使用している場合も可能です(パラメータを指定jdk.net.usePlainSocketImpl):

$ java -Djdk.net.usePlainSocketImpl -XX:+TraceClassLoading JEP353  | grep Socket
[0.037s][info   ][class,load] java.net.Socket source: jrt:/java.base
[0.039s][info   ][class,load] java.net.SocketOptions source: jrt:/java.base
[0.039s][info   ][class,load] java.net.SocketImpl source: jrt:/java.base
[0.043s][info   ][class,load] java.net.SocketImpl$$Lambda$1/0x0000000800b50840 source: java.net.SocketImpl
[0.046s][info   ][class,load] sun.net.PlatformSocketImpl source: jrt:/java.base
[0.047s][info   ][class,load] java.net.AbstractPlainSocketImpl source: jrt:/java.base
[0.047s][info   ][class,load] java.net.PlainSocketImpl source: jrt:/java.base
[0.047s][info   ][class,load] java.net.AbstractPlainSocketImpl$1 source: jrt:/java.base
[0.047s][info   ][class,load] sun.net.ext.ExtendedSocketOptions source: jrt:/java.base
[0.047s][info   ][class,load] jdk.net.ExtendedSocketOptions source: jrt:/jdk.net
[0.047s][info   ][class,load] java.net.SocketOption source: jrt:/java.base
[0.047s][info   ][class,load] jdk.net.ExtendedSocketOptions$ExtSocketOption source: jrt:/jdk.net
[0.047s][info   ][class,load] jdk.net.SocketFlow source: jrt:/jdk.net
[0.047s][info   ][class,load] jdk.net.ExtendedSocketOptions$PlatformSocketOptions source: jrt:/jdk.net
[0.047s][info   ][class,load] jdk.net.ExtendedSocketOptions$PlatformSocketOptions$1 source: jrt:/jdk.net
[0.048s][info   ][class,load] jdk.net.LinuxSocketOptions source: jrt:/jdk.net
[0.048s][info   ][class,load] jdk.net.LinuxSocketOptions$$Lambda$2/0x0000000800b51040 source: jdk.net.LinuxSocketOptions
[0.049s][info   ][class,load] jdk.net.ExtendedSocketOptions$1 source: jrt:/jdk.net
[0.049s][info   ][class,load] java.net.StandardSocketOptions source: jrt:/java.base
[0.049s][info   ][class,load] java.net.StandardSocketOptions$StdSocketOption source: jrt:/java.base
[0.051s][info   ][class,load] sun.net.ext.ExtendedSocketOptions$$Lambda$3/0x0000000800b51440 source: sun.net.ext.ExtendedSocketOptions
[0.057s][info   ][class,load] java.net.DelegatingSocketImpl source: jrt:/java.base
[0.057s][info   ][class,load] java.net.SocksSocketImpl source: jrt:/java.base
[0.058s][info   ][class,load] java.net.ServerSocket source: jrt:/java.base
[0.058s][info   ][class,load] jdk.internal.access.JavaNetSocketAccess source: jrt:/java.base
[0.058s][info   ][class,load] java.net.ServerSocket$1 source: jrt:/java.base
复制代码

上記の結果は、古い実装java.net.PlainSocketImplは、最大使用されて。

スイッチ式(プレビュー)

スイッチ12は、プレビュー機能としてJDK式に導入されます。JEP 354がこの機能を変更し、それが戻り値のyield文を紹介します。これは、ブレークを使用する必要があります(値を返さない)文を、歩留まりを使う切り替える必要式(戻り値)を切り替える、ことを意味します。

過去には、我々はスイッチの内容を返すようにしたい、それは次のように一般的な構文は、かなり面倒です。

int i;
switch (x) {
    case "1":
        i=1;
        break;
    case "2":
        i=2;
        break;
    default:
        i = x.length();
        break;
}
复制代码

でJDK13で次の構文を使用します。

int i = switch (x) {
    case "1" -> 1;
    case "2" -> 2;
    default -> {
        int len = args[1].length();
        yield len;
    }
};
复制代码

若しくは

int i = switch (x) {
    case "1": yield 1;
    case "2": yield 2;
    default: {
        int len = args[1].length();
        yield len;
    }
};
复制代码

その後、スイッチブロックの外に使用されている複数のキーワードにで切り替え、それは歩留まりで、彼が値を返すために使用しました。現在のサイクルまたは方法から直接戻り、収率は現在のブロックのうち切り替えますとの差が復帰することです。

テキストブロック(プレビュー)

12の導入生の文字列リテラルの特性JDKは、しかし、リリース前に放棄します。JEPテキスト(テキストブロック)の複数行の文字列の導入が意味で類似しています。

テキストブロックは、テキストブロックは、それが自動的にフォーマットされた文字列予測可能な方法でエスケープシーケンスのほとんどの必要性を回避し、必要に応じて開発者は、形式を制御することができ、複数行のテキスト文字列です。

次の文字列の一部の場合我々は、Javaへの外部からのテキスト文字列をコピーするために使用自動的にエスケープされます。

 <html>
  <body>
      <p>Hello, world</p>
  </body>
</html>
复制代码

Java文字列にコピーし、我々は次のように表示されます:

"<html>\n" +
"    <body>\n" +
"        <p>Hello, world</p>\n" +
"    </body>\n" +
"</html>\n";
复制代码

自動的に、これは非常に直感的ではない文字列は、JDK 13は、次の構文を使用することができるようだつまりエスケープ:

"""
<html>
  <body>
      <p>Hello, world</p>
  </body>
</html>
""";
复制代码

複数行の文字列に配置することができ、開始ターミネーター遵守、など「」、「テキストブロックを使用して、任意のは、エスケープする必要はありません。それは非常にさわやかに見えます。

このような一般的なSQL文と:

String query = """
    SELECT `EMP_ID`, `LAST_NAME` FROM `EMPLOYEE_TB`
    WHERE `CITY` = 'INDIANAPOLIS'
    ORDER BY `EMP_ID`, `LAST_NAME`;
""";
复制代码

それはさわやかな、より直感的に見えます。

概要

上記JDK13がプレビュー段階ではまだ5つの開発者のコ​​ーディングスタイルを変更することができます特性、主にテキストブロックは、式を切り替えて、2つの新機能が、これらの2つの機能が含まれています。

あなたは、Java 8(LTS)またはJava 11(LTS)を使用している場合はさらに、JDK13ないLTS(長期サポート)のバージョンは、一時的にJavaの13にアップグレードする必要はありません。

参考:openjdk.java.net/projects/jd ... metebalci.com/blog/what-i ... www.jianshu.com/p/890196bf5 ...

おすすめ

転載: juejin.im/post/5d7ee7e65188253849631823