7

可能的重复:
阴影的概念

我对在向上转换期间如何在 Java 中处理类的字段感到困惑。例如:

class SuperClass
{
    String myString = "String in SuperClass";

    public void myMethod()
    {
        System.out.println("Method in SuperClass");
    }
}

class SubClass extends SuperClass
{
    String myString = "String in SubClass";

    public void myMethod()
    {
        System.out.println("Method in SubClass");
    }
}

class Question
{
    public static void main(String[] args)
    {
        SuperClass test = new SubClass();
            // object test is an instance of SubClass
            // but I am telling the compiler to treat it as SuperClass

        test.myMethod();
        System.out.println(test.myString);

    }
}

输出:

Method in SubClass
String in SuperClass //Why is "String in SubClass" not used?

当我创建一个对象test时,它是一个SubClass类的实例;但是,我告诉编译器将其视为SuperClass. SubClass关于方法工作的一切对我来说都很清楚:如果给定的方法是为 定义的,我将只能使用 的方法SuperClass

但是,SuperClass当我尝试访问myString. test既然testSubClass我期望使用myString的一个实例SubClass,为什么没有发生这种情况?我错过了什么?

我知道我可以SubClass使用this操作符访问 myString 。例如,我可以printMyString在 SuperClass 中定义方法,并用

public void printMyString()
{
    System.out.println(this.myString);
}

在中SubClass,所以我的问题主要是关于如何在SuperClass中使用的领域test。也许我错过了一些明显的东西?

我试图寻找答案,我发现最接近的主题是Upcasting in Java and two separate object properties,虽然有帮助,但它没有回答我的问题。

先感谢您

4

2 回答 2

7

属性不能像方法一样被重载。

test.myMethod(); 

这里方法调用取决于实际对象的类型。这里对象是类型SubClass,所以SubClass调用方法。

test.myString

访问属性时,取决于引用变量的类型。这里引用变量 ietest是类型,因此可以访问 SuperClass来自的属性。SuperClass

您正在寻找的是类变量隐藏/阴影

于 2013-01-01T06:24:52.817 回答
4

Java 中的字段只是隐藏的,实际上并没有被覆盖(这并不意味着我们在尝试此操作时会遇到编译时错误,而是在真正意义上它们没有被覆盖)。

覆盖意味着应该基于对象的运行时类型而不是基于声明的类型来调用成员。

但是 Java 中的字段绑定始终是静态的,因此它仅基于对象引用的声明类型

在您给出的示例中,通过在类中声明名为“myString”SubClass的类变量,您隐藏了它将从其超类继承的SuperClass具有相同名称“myString”的类变量。

Java语言规范:

如果该类声明了一个具有特定名称的字段,则该字段的声明被称为隐藏了超类和该类的超接口中具有相同名称的任何和所有可访问的字段声明。

如果隐藏字段是静态的,则可以通过使用限定名称或使用包含关键字 super 或转换为超类类型的字段访问表达式来访问隐藏字段。

于 2013-01-01T06:25:53.910 回答