2014-02-20 53 views
0

所以这是非常基本的,但我无法得到它。让我们假设我们有2类A,B(继承A):Java覆盖参考

class A { 
     public void m() {System.out.println("AAA");} 
    } 
    class B extends A { 
     public void m() {System.out.println("BBB"); } 
    } 

我们的主类:

class Test{ 
    public static void main(String [] args){ 
     A a=new A(); B b=new B(); A x; 
     x=a; x.m(); // "AAA" 
     x=b; x.m(); // "BBB" 

     a=b; a.m(); // "BBB" 
     b=a; b.m(); // ERROR 
    }} 

我的理解是 'X' 是A型的空引用,因为没有任何对象被创建。当我键入x = a;对null的引用现在指向A的实例。如果我调用x.m(),它会打印出与AAA =相同的x = b; x.n(); “BBB”;

但是如果我创建了一个实例A,其中'a'是引用并且说b = a;它说错误。找到一个必需的B.

那么我认为'b'的引用被引用'a'覆盖,如果我现在调用b.m();它给了我“AAA”,因为它现在指向A的实例。虽然a = b;用a.m()打印“BBB”

为什么?

+0

实例的超类的不一定是子类的实例... –

回答

4

首先我只是加入一些字符类的名字:

class Animal { 
     public void m() {System.out.println("AAA");} 
    } 
    class Bee extends Animal { 
     public void m() {System.out.println("BBB"); } 
    } 

class Test{ 
public static void main(String [] args){ 
    Animal a=new Animal(); 
    Bee b=new Bee(); 
    Animal x; 

    x=a; x.m(); // "AAA" a is an animal 
    x=b; x.m(); // "BBB" b is a Bee, so it's an Animal 

    a=b; a.m(); // "BBB" A Bee is an Animal 
    b=a; b.m(); // ERROR An Animal is a Bee? What if it's a Cat? 
}} 

在情况尚不清楚,让我们创建类:

class Cat extends Animal{ 
    public void m() {System.out.println("CAT"); } 
    public void foo() {System.out.println("FOO"); } 
}; 

你可以在前面的代码Animal a=new Animal();改变通过Animal a= new Cat();,然后你会看到b=a是不正确的,因为蜜蜂不是猫。

更新:我添加了两个方法到类猫。让我们看看它是如何工作的:

// This is the obvious part: 
Cat c= new Cat(); 
c.m(); // "CAT" 
c.foo(); // "FOO" 

// Not so obvious 
Animal a2= new Cat(); // a Cat is an animal 
a2.m(); // "CAT" 
a2.foo(); //Won't compile: ERROR 

这里会发生什么?猫是一种动物,这确保它具有方法m。该方法的行为由实例本身定义。 a2是一个指向Cat实例的变量,但我们只能调用Animal定义的方法,因为a2也可以是任何其他动物,我们不知道它可能具有哪些方法。是的,这种情况下,我们知道这是一只猫,但让我们说我们有这个方法:

public Animal createAnAnimal() { 
    if (Random.nextBoolean()) { 
     return new Cat(); 
    } else { 
     return new Bee(); 
    } 
} 

无论如何,你应该阅读有关继承和接口,其中铁道部ecomplexity添加到这个东西。

+0

确定我以为我听错,但我不知道 - 如果我创建一个动物A2 =新蜂();并说a2.m();现在究竟发生了什么? (A2是动物类型,并指出蜂他是否覆盖AAA与BBB?) – dustinboettcher

+0

@Duboe我想你应该只是你的榜样测试,但无论如何,我已经添加了一些解释 –

+0

你是最棒的 - 我失踪了链接,但它现在更清晰 - 谢谢:) – dustinboettcher

0

假设你有另一个类C:

class C extends A { 
    public void m() {System.out.println("CCC"); } 
} 

那么你的代码可以修改:

A c = new C(); 
B b = c; 

这显然是不正确的,因此错误。

2

我认为你的问题是,你有一个错误的观点。

您认为,如果您设置为a = b,那么a将是B类型!但它是而不是a仍然是A类型,并且对类B的实例有参考。

所以,这就是为什么你不能将类A的值设置为B类型的变量!

A a = new A(); 
B b = new B(); 
A x; 

x = a; // x is of type A and has now a reference to an instance of type A 
x = b; // x is of type A and has now a reference to an instance of type B 

a = b; // a is of type A and has now a reference to an instance of type B 
b = a; // b is of type B and you can't set a reference to a variable of type A 
+0

Thx这是相当有用的:) – dustinboettcher