アカウント名:
パスワード:
より多くのコメントがこの議論にあるかもしれませんが、JavaScriptが有効ではない環境を使用している場合、クラシックなコメントシステム(D1)に設定を変更する必要があります。
犯人はmoriwaka -- Anonymous Coward
importとClass#forName() (スコア:1)
importで、java.util.*;とした時、java.util直下のクラスを全てローディングするわけではなくて、javac実行時に利用しているクラスのPATH(環境変数のPATHみたいな扱い)に当たりをつける為に利用されるだけ、のような気がします。
classファイルをバイナリエディタ等で開くと、java/util/Vector;とかシンボル化された文字が見えてくるので、ひょっとすると、importを使う場合の動作というのは、CLASSPATHに含められたjarのエントリ一覧(jarエントリの一覧もスラッシュで区切られた文字列になっています)から、importで指定したパッケージ名(及びクラス名)を調べて、インスタンス化するのかもしれません。
勿論、動的ローディングではなくてjavacが実行されるタイミングなので、静的ですよね。
====
次にClass#forName()
Class#forName()は、呼ばれた時点でクラスがロードされるらしいです。ロードされると言うことは、やはり、クラスローダーに登録されるって事だと思うんですが、これは、importを使った当たり付けと同じような匂いがします(CLASSPATHに追加されると見てもいいんでしょうか?) でも、なんかイメージが違う気もします。importはjavac.exeがその時点で管理するクラスローダーのようなものが当たりを付ける為の情報を渡す事になりますが、Class#forName()はjava.exeが管理するクラスローダーに当たりを付ける情報を渡す事になるんでしょうか。
うーん、javacは、煩雑なCLASSPATHから拾った利用されているクラスのパスだけをまとめて中間ファイルを生成するのが仕事で、javaは中間ファイルに書かれた利用されているクラスのパスを疑いなしに読んでインスタンス化して実行する、という感じでしょうか。そうすると、Class#forName()で必要か不要か解らないけど兎に角読んだクラスのパスとかはどこに保持されるんでしょうね。Classクラスのオブジェクト(クラスのパスを保持するオブジェクト)として存在するとすれば、やはりGCの管轄になるんでしょうか。
====
結論を言えば、importでjava.util.*;とする事とDiscoveryで対象パッケージ下にあるクラスを総当りで探して実装クラスを見つけるのと、変わりがなさそうです。ただし、import java.util.Vector;というような必要最小限の指定と比べると、当たりを付けて探すという動作と、一時的なクラス一覧を確保する分だけ無駄があるように思えます。なので、何度も探索を行うようなロジックを組むのは、考え物だと思いました。
====
そういう事を考えてみると、プラグイン機能の場合は、特定インタフェースの実装クラスを探すのは1回だけで、その後はその実装クラスから必要なオブジェクトを生成していくような感じで作っていくのがスマートな気がしてきました。いわゆる、エントリポイントとしての実装クラスの断定です。
俯瞰しよう。何事も俯瞰しなくちゃ駄目だ。