this and super in java

You are correct that both this and super are keywords. The Java language specification defines explicitly how they must behave. The short answer is that these keywords behave specially because the specification says that they must.

According to the specification this can be used a primary expression (only in certain places) or in an explicit constructor invocation.

The keyword this may be used only in the body of an instance method, instance initializer or constructor, or in the initializer of an instance variable of a class. If it appears anywhere else, a compile-time error occurs.

So you can use this as an argument to a function to pass a reference to the current object. However note that you cannot use super in the same way as it is not a primary expression:

public class Program
{   
    void test(Program p) {}

    void run() { test(super); }

    public static void main(String[] args)
    {
        new Program().run();
    }
}

Result:

Program.java:5: '.' expected
    void run() { test(super); }

You can use super.foo though because this is defined in 15.11 to be valid:

FieldAccess:
    Primary . Identifier
    super . Identifier
    ClassName .super . Identifier

The specification also puts restrictions on how super can be used:

The special forms using the keyword super are valid only in an instance method, instance initializer or constructor, or in the initializer of an instance variable of a class; these are exactly the same situations in which the keyword this may be used (§15.8.3).


The Java language provides specific handling for these two keywords and they are allowed in limited contexts.

Invoking this(...) will result in bytecode that will invoke the corresponding constructor on the current class, while invoking super(...) will result in bytecode that will invoke the corresponding constructor on the supertype.

Java provides special handling for these because their binding is different from that of normal methods (i.e., you want to avoid dynamic invocation, or you would never manage to get the constructor on the supertype).

Every language has to deal with this problem. In C++, for example, you explicitly specify the name of the parent method instead of using super.

Tags:

Java