1. 序章

この記事では、 Java仮想マシン(JVM) Dalvik仮想マシン(DVM)の違いについて説明します。 まず、それぞれについて簡単に説明してから、比較します。

Android 5.0以降、Dalvik仮想マシンはAndroidランタイム(ART)に置き換えられていることに注意してください。

2. ランタイムとは何ですか?

ランタイムシステムは、Javaなどの高級言語で記述されたコードをマシンコードに変換し、中央処理装置(CPU)が理解できる環境を提供します。

これらのタイプの翻訳者を区別できます。

  • アセンブラ:アセンブリコードをマシンコードに直接変換するため、高速です
  • コンパイラ:コードをアセンブリコードに変換し、次にアセンブラを使用して結果のコードをバイナリに変換します。 この手法の使用は低速ですが、実行は高速です。 また、結果のマシンコードはプラットフォームに依存します
  • 通訳者:実行中にコードを翻訳します。 変換は実行時に行われるため、実行が遅くなる可能性があります

3. Java仮想マシン

JVMは、Java デスクトップ、サーバー、およびWebアプリケーションを実行するための仮想マシンです。 Javaのもう1つの重要な点は、移植性を念頭に置いて開発されたことです。 したがって、 JVMは、複数のホストアーキテクチャをサポートし、どこでも実行できるように形作られています。 ただし、組み込みデバイスには重すぎます。

Javaには活発なコミュニティがあり、今後も広く使用されます。さらに、HotSpotはJVMリファレンス実装です。 同様に、オープンソースコミュニティによって維持されている他の5つ以上の実装もあります。

新しいケイデンスベースのリリースでは、JavaとJVMは6か月ごとに新しい更新を受け取ります。 たとえば、 Foreign-MemoryAccessPackagingToolなどの次のリリースの提案を一覧表示できます。

4. Dalvik仮想マシン

DVMは、Androidアプリケーションを実行するための仮想マシンです。 DVMは、Java言語で記述されたプログラムからコンパイルされたDalvikバイトコードを実行します。 DVMはJVMではないことに注意してください。

DVMの重要な設計原則の1つは、低メモリモバイルデバイスで実行し、どのJVMよりも高速にロードする必要があるということです。 また、このVMは、同じデバイスで複数のインスタンスを実行する場合に効率的です。

2014年、GoogleはAndroid5用のAndroid Runtime(ART)をリリースしました。これは、アプリケーションのパフォーマンスのバッテリー使用量を改善するためにDalvikに取って代わりました。 最後のバージョンはAndroid4.4では1.6.0でした。

5. JVMとDVMの違い

5.1. 建築

JVMはスタックベースのVMであり、すべての算術演算と論理演算がプッシュおよびポップオペランドを介して実行され、結果がスタックに格納されます。 スタックは、メソッドを格納するためのデータ構造でもあります。

対照的に、DVMはレジスタベースのVMです。 CPUにあるこれらのレジスタは、すべての算術演算と論理演算を実行します。 レジスタは、オペランドを格納するためのデータ構造です。

5.2. コンパイル

Javaコードは、JVM内で Javaバイトコード(。classファイル)と呼ばれる中間形式にコンパイルされます。 次に、JVM は結果のJavaバイトコードを解析し、それをマシンコードに変換します。

Androidデバイスでは、DVMはJavaコードをJVMのようなJavaバイトコード(.classファイル)と呼ばれる中間形式にコンパイルします。 次に、 Dalvik eXchangeまたはdxというツールを使用して、JavaバイトコードをDalvikバイトコードに変換します。 最後に、DVMはDalvikバイトコードをバイナリマシンコードに変換します。

両方のVMは、Just-In-Time(JIT)コンパイラを使用します。 JITコンパイラは、実行時にコンパイルを実行するコンパイラの一種です。

5.3. パフォーマンス

前に見たように、JVMはスタックベースのVMであり、DVMはレジスタベースのVMです。 オペランドの位置は暗黙的にオペランドスタック上にあるため、スタックベースのVMバイトコードは非常にコンパクトです。 レジスタベースのVMバイトコードでは、すべての暗黙のオペランドが命令の一部である必要があります。 これは、レジスタベースのコードサイズが通常、スタックベースのバイトコードよりもはるかに大きいことを示しています。

一方、レジスタベースのVMは、対応するスタックベースのVMよりも少ないVM命令を使用して計算を表現できます。 VM命令のディスパッチにはコストがかかるため、実行される VM命令を減らすと、レジスタベースのVMの速度が大幅に向上する可能性があります。

もちろん、この区別は、VMを解釈モードで実行している場合にのみ関係します。

5.4. 実行

実行中のアプリケーションごとにJVMのインスタンスをセットアップすることは可能ですが、通常、デプロイしたすべてのアプリケーションを実行するために、共有プロセスとメモリスペースを使用してJVMの単一インスタンスのみを構成します。

ただし、Androidは複数のDVMインスタンスを実行するように設計されています。 そのため、アプリケーションまたはサービスを実行するために、 Android OSは、共有メモリスペースに別のプロセスを持つ新しいDVMインスタンスを作成し、アプリケーションを実行するためのコードをデプロイします。

6. 結論

このチュートリアルでは、JVMとDVMの主な違いを紹介しました。 どちらのVMもJavaで記述されたアプリケーションを実行しますが、コードのコンパイルと実行には異なる手法とプロセスを使用します。