モジュール java.base
パッケージ java.lang

クラスClassLoader

java.lang.Object
java.lang.ClassLoader
直系の既知のサブクラス:
SecureClassLoader

public abstract class ClassLoader extends Object
クラス・ローダーは、クラスのロードを担当するオブジェクトです。 クラスClassLoaderは抽象クラスです。 クラスのバイナリ名を指定すると、クラス・ローダーはクラスの定義を構成するデータを見つけるか生成します。 一般的な方法としては、名前をファイル名に変換して、ファイル・システムからその名前の「クラス・ファイル」を読み込みます。

すべてのClassオブジェクトには、そのオブジェクトを定義したClassLoaderへのreferenceが含まれます。

配列クラスのClassオブジェクトは、クラス・ローダーでは作成されませんが、Javaランタイムで必要とされるとおりに自動的に作成されます。 配列クラスのクラス・ローダー(Class.getClassLoader()から返される)は、その要素の型のクラス・ローダーと同じになります。要素の型がプリミティブ型の場合、配列クラスはクラス・ローダーを持ちません。

アプリケーションは、Java仮想マシンがクラスを動的にロードする方法を拡張するために、ClassLoaderのサブクラスを実装します。

クラス・ローダーは一般的に、セキュリティ・マネージャがセキュリティ・ドメインを示すために使われます。

クラスをロードすることに加えて、クラス・ローダーはリソースの特定も担当します。 リソースは、抽象的な'/'-separatedパス名で識別されるデータ(".class"ファイル、構成データ、またはイメージなど)です。 リソースは通常、アプリケーションまたはライブラリにパッケージ化されているため、アプリケーションまたはライブラリ内のコードでリソースを見つけることができます。 場合によっては、リソースが他のライブラリに配置されるように含まれています。

ClassLoaderクラスは、委任モデルを使用してクラスおよびリソースを検索します。 ClassLoaderの各インスタンスには、関連付けられた親クラス・ローダーがあります。 ClassLoaderインスタンスは、クラスまたはリソースの検索をリクエストされると、そのクラスまたはリソース自体の検索を試みる前に、そのクラスまたはリソースの検索を親クラス・ローダーに委譲します。

クラスの同時ロードをサポートするクラス・ローダーは、並列対応クラス・ローダーと呼ばれ、ClassLoader.registerAsParallelCapableメソッドを呼び出してクラス初期化時に自身を登録する必要があります。 ClassLoaderクラスは、デフォルトでパラレル対応として登録されています。 ただしそのサブクラスについては、並行可能な場合には自身を登録する必要があります。 委任モデルが厳密に階層化されていない環境では、クラス・ローダーはパラレルに対応している必要があります。そうしないと、クラス・ロード・プロセス(loadClassメソッドを参照してください)の間、ローダー・ロックが保持されるため、クラス・ロードによってデッドロックが発生する可能性があります。

ランタイム組み込みクラス・ローダー

Javaランタイムには、次の組み込みクラス・ローダーがあります:
  • ブートストラップ・クラス・ローダー。 これは、仮想マシンの組込みクラス・ローダーで、通常はnullとして表され、親を持ちません。

  • 「プラットフォーム・クラス・ローダー」 プラットフォーム・クラス・ローダーは、「プラットフォーム・クラス」のロードを担当します。 プラットフォーム・クラスには、Java SEプラットフォームAPI、その実装クラス、およびプラットフォーム・クラス・ローダーまたはその祖先によって定義されたJDK固有のランタイム・クラスが含まれます。 プラットフォーム・クラス・ローダーは、ClassLoaderインスタンスの親として使用できます。

    プラットフォーム・クラス・ローダーに定義されたモジュールのアップグレード/オーバーライドを可能にするために、アップグレードされたモジュールが定義されたモジュールをプラットフォーム・クラス・ローダーとその祖先以外のクラス・ローダーに読み込む場合、プラットフォーム・クラス・ローダーは他のクラス・ローダーに委譲する必要があります。アプリケーション・クラス・ローダーなどがあります。 言い換えれば、プラットフォーム・クラス・ローダーとその祖先以外のクラス・ローダーに定義された名前付きモジュールのクラスは、プラットフォーム・クラス・ローダーに可視である可能性があります。

  • 「システム・クラス・ローダー」 「アプリケーション・クラス・ローダー」とも呼ばれ、プラットフォーム・クラス・ローダーとは異なります。 システム・クラス・ローダーは、通常、アプリケーション・クラス・パス、モジュール・パスおよびJDK固有のツールでクラスを定義するために使用されます。 プラットフォーム・クラス・ローダーはシステム・クラス・ローダーの親または祖先であるため、システム・クラス・ローダーはその親に委任することでプラットフォーム・クラスをロードできます。

通常、Java仮想マシンは、プラットフォームに依存しない方法でローカル・ファイル・システムからクラスをロードします。 ただし、ファイルから作成できないクラスもあります。このようなクラスは、ネットワークなどのほかのソースから作成したり、アプリケーションが構築したりします。 メソッドdefineClassは、バイトの配列をクラスClassのインスタンスに変換します。 この新たに定義されたクラスのインスタンスは、Class.newInstanceを使用して作成できます。

クラス・ローダーで作成したオブジェクトのメソッドとコンストラクタは、ほかのクラスを参照できます。 参照されるclass(es)を決定するために、Java仮想マシンは、最初にクラスを作成したクラス・ローダーのloadClassメソッドを呼び出します。

たとえば、アプリケーションはネットワーク・クラス・ローダーを作成して、サーバーからクラス・ファイルをダウンロードできます。 コードは次のようになります。

   ClassLoader loader = new NetworkClassLoader(host, port);
   Object main = loader.loadClass("Main", true).newInstance();
        . . .
 

ネットワーク・クラス・ローダー・サブクラスは、ネットワークからクラスをロードするために、メソッドfindClassおよびloadClassDataを定義する必要があります。 クラスを構成するバイトをダウンロードしたら、メソッドdefineClassを使用してクラス・インスタンスを作成する必要があります。 実装の例を次に示します。

     class NetworkClassLoader extends ClassLoader {
         String host;
         int port;

         public Class findClass(String name) {
             byte[] b = loadClassData(name);
             return defineClass(name, b, 0, b.length);
         }

         private byte[] loadClassData(String name) {
             // load the class data from the connection
              . . .
         }
     }
 

バイナリ名

ClassLoaderのメソッドにStringパラメータとして提供されるクラス名は、「Java言語仕様」で定義されているバイナリ名である必要があります。

次に、有効なクラス名の例を示します。

   "java.lang.String"
   "javax.swing.JSpinner$DefaultEditor"
   "java.security.KeyStore$Builder$FileBuilder$1"
   "java.net.URLClassLoader$3$1"
 

ClassLoaderのメソッドへのStringパラメータとして指定されたパッケージ名は、空の文字列(名前のないパッケージを示す)または「Java言語仕様」で定義された完全修飾名でなければなりません。

Java言語仕様を参照してください:
6.7 完全修飾名
13.1バイナリの形式
導入されたバージョン:
1.0
関連項目: