A.java
public class A {
String val = "A";
void print() {
System.out.println(val);
}
}
B.java
public class B extends A {
String val = "B";
@Override
void print() {
System.out.println(val);
}
}
これらのクラスを用いて以下を実装&実行
Main.java
public class Main {
public static void main(String[] args) {
A a = new A();
// BクラスはAクラスを継承しているため変数の型としてAが使用できる
A b = new B();
// bの型がAであるため、valはA型に定義されたフィールドの値が使用される
System.out.println("aのvalを表示 : " + a.val); // A
System.out.println("bのvalを表示 : " + b.val); // A
System.out.print("aのprint()メソッドを実行 : ");
a.print(); // A
System.out.print("bのprint()メソッドを実行 : ");
b.print();// B
}
}
b.valを表示すると「A」が表示されるのは
変数bの型としてAを使用しており、Aのフィールドが使用されるため。
一方でb.print()で「B」が表示されるのは
Bクラスではprint()メソッドがオーバーライドされており、new B()をした時点でBクラスのメソッドが優先されるため。
メソッドはオーバーライドされるけれど、変数はフィールドに紐づいているので挙動が変わることに注意しましょう