なにか解決方法はあるでしょうか?
import に書けないだけで、A.class を classpath がとおったフォルダに置いておけば、Class. forName("A") でデフォルトパッケージのクラスAをClassLoaderに読み込ませることはできます。
Class#newInstance() でのインスタンスの生成もできます。
とここまでは確認済。
それがjarに入っている場合は確認してませんが、classpathが通ってさえいれば同じ様にできるのではないかなあ、と楽観視してます。
で、ここからはアイデア。
頻繁に使わないし頻繁に呼び出されることもないケース
リフレクション経由で使う。
色々な所で使うが頻繁に呼び出されることはないケース
リフレクション経由で呼び出すラッパーを作る。
ほとんど依存していると言ってもいいぐらい使っているケース
名前付きpackage に(アプリ本体とは別の package にした方が依存関係を集約できていいと思う) interface InterfaceA を作って、A のメソッドとフィールド変数のget/setメソッドを定義。
デフォルトパッケージに class WrapperA implements InterfaceA を作って、Aのインスタンスを生成した後、メソッドは全部Aに委譲してしまう様に実装。
名前付きpackageの方にユーティリティメソッド
public static InterfaceA newInstaceA() { Class c = Class.forName("WrapperA"); return (InterfaceA)c.newInstance(); }
の様な感じのメソッドを作っておくとして、本体プログラムは InterfaceA を相手にするように書く。
というような感じにするといいのではないでしょうか。
おおー、なるほど
importができなくても、リフレクションで取得することはできてしまうわけですね!それは気づきませんでした!
やっぱりそうですよねぇ。
実はコンパイルされる前の(ツールによって生成された)ソースも手に入るので、それらにパッケージ宣言を付け足してコンパイルしてJARにまとめるツールを作ればいいわけですが…うーむ。
やっぱりコンパイルされてしまったらいじるのは至難ですか。