class OuterA {
class InnerA {
}
}
class SubclassC extends OuterA.InnerA {
SubclassC(OuterA outerRef) {
outerRef.super();
}
}
class XYZ {
public static void main(String[] args) {
new SubclassC(new OuterA());
}
}
In the above code
OuterA
object reference to SubclassC
constructor for the .java file to compile?InnerA
object reference not required to be passed to SubclassC
constructor?Why do I need to pass OuterA object reference to SubclassC constructor for the .java file to compile?
Because SubclassC
extends the definition of the InnerA
class. Meanwhile, InnerA
class is bound to OuterA
(i.e. all the instances of InnerA
will be bound to a corresponding instance of OuterA
). Therefore, to obtain an instance of SubclassC
, you need an instance of OuterA
.
Why is InnerA object reference not required to be passed to SubclassC constructor?
Because when creating a SubclassC
, under the hood, an instance of its superclass will be created first, i.e there will be a instance of InnerA
. You can actually look on SubclassC
as a special kind of InnerA
.
- Why do I need to pass OuterA object reference to SubclassC constructor for the .java file to compile?
Because InnerA
is an inner class of OuterA
. This means that an object of type OuterA.InnerA
or any of its subtypes, such as SubclassC
, can only exist in the context of an enclosing class (OuterA
in this case) instance.
This is called a Qualified superclass constructor invocation. From the JLS:
Qualified superclass constructor invocations begin with a Primary expression . They allow a subclass constructor to explicitly specify the newly created object's immediately enclosing instance with respect to the direct superclass (§8.1.3). This may be necessary when the superclass is an inner class.
If you don't need to link the SubclassC
instance to an already existing instance of OuterA
, you can create the new OuterA
object in the SuperclassC
constructor:
static class SubclassC extends OuterA.InnerA {
SubclassC() {
new OuterA().super();
}
}
- Why is InnerA object reference not required to be passed to SubclassC constructor?
Since SubclassC
extends OuterA.InnerA
, when you do outerRef.super()
you are calling the OuterA.InnerA
constructor. To see that this is the case, consider the code below:
public class Example {
static class OuterA {
OuterA() {
System.out.println("Call OuterA constructor");
}
class InnerA {
InnerA() {
System.out.println("Call InnerA constructor");
}
}
}
static class SubclassC extends OuterA.InnerA {
SubclassC(OuterA outerRef) {
outerRef.super();
System.out.println("Call SuperclassC constructor");
}
}
public static void main(String[] args) {
OuterA outerA = new OuterA();
System.out.println("Before new SuperclassC()");
new SubclassC(outerA);
}
}
Output:
Call OuterA constructor
Before new SuperclassC()
Call InnerA constructor
Call SuperclassC constructor
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With