フィールドタイプをオーバーロードして別のフィールドタイプにすることは可能ですか?
もしそうなら、いくつかの例を提供することは可能でしょうか?
フィールドをオーバーロードすることはできません(メソッドのみをオーバーロードできます)。フィールドのオーバーライドと混同される可能性があります。とにかく不可能ですが、スーパークラスからフィールドを非表示にすることになります。この投稿を見てください。
Javaはインターフェースをサポートしていると思います。インターフェースは、達成しようとしていることを達成するのに役立つはずです。
パブリックメンバーにそのように過負荷をかけないように注意してください。
このコードを見てください
class A<T> {
protected T field1;
}
class B extends A<String> {
public char field1;
public static void main(String[] args) {
A a = new B();
a.field1 = 12442;
}
}
例外なく実行されます。field1がオーバーライドされた場合、例外が発生するはずですが、発生しません。
また、これは例外なく実行されます
class A<T> {
protected T field1;
}
class B extends A<Character> {
public char field1;
public static void main(String[] args) {
A a = new B();
a.field1 = 12442;
}
}
それは不可能だ
Java言語(JLS)はそれを許可しませんが、Javaバイトコード(JVMS)は許可します
Oracle JDK 1.8.0_45は、を実装するためにこれに依存していますassert
。例えば:
public class Assert {
static final int[] $assertionsDisabled = new int[0];
public static void main(String[] args) {
System.out.println(int.length);
assert System.currentTimeMillis() == 0L;
}
}
Oracle JDK 1.8.0_45
1つは明示的(int[]
)、もう1つは合成( )の2つを生成bool
し、それらをうまく区別できます。しかし、私たちが宣言した場合:
static final boolean $assertionsDisabled = false;
次のコマンドではコンパイルに失敗します:
the symbol $assertionsDisabled conflicts with a compile synthesized symbo
詳細については、 https://stackoverflow.com/a/31355548/895245を参照してください。
それが不可能である理由の考えられる理由
問題は、フィールドのタイプを判別できないことです。検討:
void f(int i) { System.out.println("int"); }
void f(float i) { System.out.println("float"); }
int i;
float i;
// Which overridden method is called?
void m() { f(i); }