简体   繁体   English

子类对象的超类引用变量访问子类的属性而不是父类的属性

[英]Super-class reference variable to a sub-class object accesses the subclass's attribute instead of the super's

In my code, I have 3 classes: class A在我的代码中,我有 3 个类: A

public class A {
    int x = 1;
    static double y = 3.0;
    public A() {
    x = (int)y;
    }
    public A(int x) {
    this .x = this . getX () + x;
    }
    int getX () {
    return this .x;
    }
    public void f( float z) {
    y *= z;
    }
}

class B , which extends AB ,它扩展了A

public class B extends A {
    int x = 7;
    public B(int x) {
    super (x);
    this .x = x;
    }
    public B() {
    this .y += 1.0;
    }
    int getX () {
    return this .x;
    }
    public void f( long z) {
    y += z;
    }
    public void f( double z) {
    y -= z;
    }
}

and class M , which includes the main function和类M ,其中包括main功能

public class M {
    public static void main ( String [] args ) {
        A a1 = new A();
        System .out. println (a1.x + " " + A.y); // OUT: [ ] [ ]
        B b1 = new B();
        System .out. println (b1.x + " " + A.y); // OUT: [ ] [ ]
        System .out. println ((( A)b1 ).x); // OUT: [ ]
        A ab = new B (5);
        System .out. println (ab.x + " " + A.y); // OUT: [ ] [ ]
        System .out. println ((( A)ab ).x); // OUT: [ ]
        A.y = 5.0;
        b1.f (2.0f);
        System .out. println (A.y); // OUT: [ ]
        ab.f (5);
        System .out. println (A.y); // OUT: [ ]
        }
}

Every called function in the main method behaves as expected except for the following two:除了以下两个函数外, main方法中的每个被调用函数都按预期运行:

        A ab = new B (5);
        System .out. println (ab.x + " " + A.y); // OUT: [ ] [ ]
        System .out. println ((( A)ab ).x); // OUT: [ ]

which gives这使

5 4.0
5

as output, while I expect it to give作为输出,而我希望它给出

6 4.0
6

Now, as far I understand, upon creating a new object of type B , which is referred to by the reference variable ab of type A , and after invoking the right constructors, the variable x in the super-class should have the value of 6 , while the other x in the sub-class equals 5 .现在,据我所知,在创建类型的新对象B ,其通过引用变量称为ab型的A ,并调用正确的构造后,变量x在超类应该具有的值6 ,而子类中的另一个x等于5

If this is right, then, shouldn't ab.x refer to the x in the super-class, which equals 6 , since attributes and static methods (in contrary to non-static methods) are dealt with in compile time, which means that the println method should print the variable, within the same class as the reference variable type?如果这是对的,那么ab.xab.x引用超类中的x ,它等于6 ,因为属性和静态方法(与非静态方法相反)是在编译时处理的,这意味着println方法应该在与引用变量类型相同的类中打印变量吗?

And in case of (( A)ab ).x) shouldn't the x in class B be invisible after casting ab ?(( A)ab ).x)情况下, B类中的x在投射ab后不应该是不可见的吗?

I'd be thankful if you can guide me through, why this is happening.如果您能指导我完成,我将不胜感激,为什么会发生这种情况。

This statement this.x = this.getX() + x; in A constructor这个语句this.x = this.getX() + x; in A constructor this.x = this.getX() + x; in A constructor will call getX from B so the variable x in the super-class will have the value of 5 not 6 . this.x = this.getX() + x; in A constructor getX from B调用getX from B因此超类中的变量 x 的值将是5而不是6

So when you call this statement所以当你调用这个语句时

A ab = new B (5);

Flow will be流将是

It will call parameterized constructor in class B , then it will encounter super(x) statement, so it will call parameterized constructor in class A where you have this statement this.x = this.getX() + x;它将调用class B参数化构造函数,然后它会遇到super(x)语句,因此它将调用class A中的参数化构造函数,其中您有这个语句this.x = this.getX() + x; which will call getX() of class B which will return this.x ( here x value be returned as 0 ) so the final value of this.x = this.getX() + x;它将调用class B getX()它将返回this.x (这里 x 值返回为0 )所以this.x = this.getX() + x;的最终值this.x = this.getX() + x; is (0+5 = 5), and this.x will have a final value of 5. This way in both class A and class B variable x value will be 5.是 (0+5 = 5),this.x 的最终值为 5。这样在class A class Bclass B变量中, x值都是 5。

That is why your following statements are returning这就是为什么您的以下语句返回的原因

System .out. println (ab.x + " " + A.y); // OUT: [5] [3.0]
System .out. println ((( A)ab ).x); // OUT: [5]

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM