私は最近遭遇しましたなぜJava5+APIは共変リターンタイプを利用しないのですか?。
私は質問に同意します。Java5では、JDK開発者はクローンに共変リターン型を使用し、既存のクラスを変更して、次のように記述できた可能性があります。
ArrayList<String> list = new ArrayList<String>();
ArrayList<String> clone = list.clone();
それ以外の
ArrayList<String> clone = (ArrayList<String>)list.clone();
しかし、いくつかの理由で、はそれをしませんでした。
test.ArrayList.clone
リターンタイプをObjectからArrayListに変更して、「以前にコンパイルされたクラスが新しいリターンタイプのメソッドを見つけることができない」かどうかを確認するためにいくつかの実験を行いましたが、問題を再現できませんでした。バイトコードでは、oldへの呼び出しはtest.ArrayList.clone
次のようになります
INVOKEVIRTUAL test.ArrayList.clone()Ljava/lang/Object;
つまり、メソッドのシグネチャにはリターンタイプが含まれているため、変更後、そのシグネチャはに変更されtest.ArrayList.clone()Ltest.ArrayList
ます。したがって、古いクラスは壊れているように見えますが、実際には、test.ArrayList.classに2つのクローンメソッドがあるため、壊れません。
public clone()Ltest.ArrayList;
public bridge clone()Ljava/lang/Object;
2つ目はブリッジで、共変バージョンを呼び出すだけです。
...
INVOKEVIRTUAL ArrayList.clone()Ltest.ArrayList;
...
そのため、古いクラスは問題なく動作し続けます。
クローンのリターンタイプを変更するとバイトコードが壊れることを誰かが説明できますか?