0

Consider the following code:

class Person {
    String className = "Person";

    void printClassName () {
        System.out.println("I am " + this.className);
        System.out.println("I am " + this.getClass().getSimpleName());
    }
}

class Employee extends Person {
    // intentionally hiding this field
    String className = "Employee";
}

public class App {
    public static void main(String[] args) {
        Employee raghu = new Employee ();
        raghu.printClassName();
    }

}

I have a few questions.

  1. When an object of subclass is created, how many objects are actually created? Only one, extending the properties of superclass by introducing new properties defined in subclass? Or two, the subclass object that we have access to and a superclass object, whose existence is hidden from us?

  2. If two objects are created, which object is in charge when a non-overridden method is invoked on the subclass object? In other words, what does this refer to inside a non-overridden method? The hidden superclass object or the subclass object?

  3. If your answer for #2 is the hidden object of superclass, then why the code above prints "I am Employee" for System.out.println("I am " + getClass().getSimpleName()); inside printClassName.

  4. If your answer for #2 is the object of subclass, then why the first line inside printClassName prints "I am Person"?

2 Answers2

1

You declare the variable as type Employee

this.className

refers to the className in that class.

this.getClass().getSimpleName()

this.getClass() returns the class Employee, since that's how you declared the variable, which is why the getSimpleName() returns "Employee"

Stultuske
  • 9,296
  • 1
  • 25
  • 37
  • I strongly believe that `this` always refers to the object on which a method is called. But can you elaborate why first line in `printClassName` prints what it prints. –  Feb 15 '18 at 14:09
  • 1
    a superclass doesn't really know about subclasses (unlike the other way around). the moment you put 'this.className' and in that class it finds that variable, it's a 'done deal'. you may be hiding it within the subclass, but you are calling it in the parent class, where it still has access to the hidden variable. (yes, it is referring to the current instance), this is what you get if you create a new variable with the same name. (and why doing so is not encouraged) – Stultuske Feb 15 '18 at 14:13
0

The field className in the child class Employee is an extra second field having the same name as the field className in Person; this is called shadowing. There is no inheritance for fields.

(Probably known.)

class Employee extends Person { // Manner to change the super field
    Employee() {
        className = "Employee";
    }
}
  1. new Employee() creates one object holding two className fields. It calls the super constructor, does the field initialisations, and executes the rest of the constructor code.

  2. this always is the sole object, possibly of some child class. So a Person.this might actually be an Employee.

  3. and 4. this.className in Person for an Employee object simply will access the Person field, as there is no inheritance for fields. In contrast the method xxx() will call the child most method.

Joop Eggen
  • 107,315
  • 7
  • 83
  • 138