Syntax for calling super

Dan Smith daniel.smith at oracle.com
Mon Aug 27 11:19:09 PDT 2012


On Aug 27, 2012, at 10:57 AM, Peter Levart <peter.levart at marand.si> wrote:

> The result of the example I gave might actualy be a bug in the compiler (which 
> I reported in a separate message).
> 
> But what should actualy be the result anyway?
> 
> Does K.super.m() in anonymous inner class:
> 
> new K() {
>    @Override
>    public void m() {
>       K.super.m();
>    }
> }
> 
> where K is an interface with default method m() actualy call the K.m() with 
> the target being an annonymous instance or does the call refer to the outer 
> instance (which is also a class directly implementing K)?
> 
> What about if there are several outer classes that all directly implement K 
> and you don't want to choose the innermost?

There is no feature (in the current JSR 335 spec) to refer to a superinterface method of an enclosing instance.  The rule for 'Foo.super' is that 'Foo' must refer to either a lexically enclosing class name or a direct superinterface of the immediately enclosing class.  Otherwise, it's an error.

> 
> Does EG consider such situations to be so rare that it is not worth supporting 
> them?
> 
> I can understand that resolving a conflicting default methods inherited from 
> two or more interfaces might be way more common, so K.super.m() is the best 
> syntax (so far) for selecting the right method, but there should also be a 
> (maybe less perfect) way of selecting the outer instance and the super 
> interface independently and at the same time.
> 
> The syntax I suggested might not be the best for that considering K.super.m() 
> is to also select superinterface's default methods, but what about an 
> alternative one:
> 
> If we accept:
> 
>    this.super.m()
> 
> to be a longer version of:
> 
>    super.m()
> 
> (there are analogues already in Java: this.m() vs. m(); this.x vs. x)

Reasonable...

> then we can extend and combine this into specifying the instance and the 
> superinterface independently:
> 
> public class A implements J, K {
> 
>    public void m() { ... }
> 
>    class B implements K {
>        public void m() {
>            super.m(); // is the same as
>            this.super.m(); // and in this example the same as more specific
>            K.super.m(); // which is the same as
>            this.K.super.m(); // but
> 
>            A.this.K.super.m(); 
>           // can be used to select A outer instance's K superinterface method
>        }
>    }
> }

To avoid a tangled mess, ideally this syntax would work so that the way to refer to the a super method of an enclosing class were:

Outer.this.super.m();

rather than:

Outer.super.m();

Unfortunately, that ship has sailed...

An interesting suggestion, in any case.

—Dan


More information about the lambda-dev mailing list