Programming Languages‎ > ‎Java‎ > ‎

07. Java Inheritance (Part 1)


In Java, you may create subclasses that reuse and extend another class, so that the subclass inherits (has direct access to) certain members (variables & methods) of its superclass.  (A Java subclass is like a C++ derived class). 

Why is inheritance useful?  The design of a program is better when you create classes for more general features, and subclasses for more detailed features.  We'll see some examples of this later.

What's different about subclasses from a regular class?
  • when an object of a subclass is instantiated, all of the instance variables in the superclass (and its superclass, etc.) are allocated memory along with the subclass' instance variables

  • non-private* methods in its superclass (and its superclass, etc.)  may be called on a subclass object, as well as the subclass' (non-private) methods

  • when inside a subclass instance method, the superclass (non-private) methods may be called (if the superclass method is not overriden in the subclass)

  • when inside a subclass instance method, the superclass (non-private) variables may be directly accessed (unless the subclass has a variable with the same name)

Differences from C++:

  • Java does NOT support multiple inheritance, i.e., each class may only haveone superclass (unlike C++).

  • Java allows implementing more than one interface (see p. 16).

  • Every Java class may be subclassed unless it is declared as final.

  • The default superclass for all classes isjava.lang.Object (details later)

 *Non-private methods include public, protected or no access specifier (protected superclass members are accessible by methods of a subclass in the same or different package and non-subclasses in the same package)

Defining a Subclass

In the class heading, add the extends class:  class subclass-id extends superclass-id
Optional: You may define the class as public


public class SuperClass{

  int packageVar;
  public int publicVar;
  private int privateVar;
  protected int protectedVar;

} // end class SuperClass

public class SubClass1 extends SuperClass{

  void someMethod(){

     packageVar = 0; // OK if in same package
     publicVar = 0; // OK
     privateVar = 0; // Error
     protectedVar = 0; // OK


} // end class SubClass1

// In another package:
public class SubClass2 extends SuperClass{

void someMethod(){

     packageVar = 0; // Error
     publicVar = 0; // OK
     privateVar = 0; // Error
     protectedVar = 0; // OK


} // end class SubClass

public class Main{

  public static void main( String [] args ){
       SubClass1 sub1 = new SubClass1();
       sub1.packageVar = 0; // Error
       sub1.publicVar = 0; // OK
       sub1.privateVar = 0; // Error
       sub1.protectedVar = 0; // Error

       SubClass2 sub2 = new SubClass2();
       sub2.packageVar = 0; // Error
       sub2.publicVar = 0; // OK
       sub2.privateVar = 0; // Error
       sub2.protectedVar = 0; // Error
  } // end main

} // end class Main

NOTE: When no access specifier is given for a class, method or variable, then it can only be accessed by all methods in the same package.

More on Subclasses

Inside a Subclass:

  • In the subclass' constructor(s) you may call a superclass constructor just by doing (must be thefirst statement in the subclass' constructor):  super( parameters);
    NOTE: If you DON'T explicitly call the superclass constructor, then the JVM will try to call its default constructor (which may not exist)!
  • You may call a superclass non-private method if no method in the subclass has the same name by calling as if it’s in the same class
  • You may override a superclass method in the subclass (defining it with the exact same name and same parameters)-- this triggers polymorphism(read more about polymorphism HERE)
  • If the superclass has the same name method as in the subclass, to call it, do: super.method-id(parameters)
  • You may assign a subclass object (reference) to a superclass object variable
  • When a subclass constructor passes a parameter up to the superclass constructor via the superkeyword, the parameter cannot be a class-scope instance variable of the subclass because the subclass hasn't been constructed yet.  Example extending the Grandparent class on next page:

    public class BadParent extends Grandparent{
         private int data=1;
         public BadParent(){
              super(data); // Error: can't pass data
    } // end class BadParent


Example of Using Inheritance

public class Grandparent{

protected int data;
public Grandparent(int i){
} // end Grandparent constructor

public void display(){
       System.out.println("Grandparent display "+data);
} // end display method

} // end Grandparent class

public class Parent extends Grandparent{

protected int data; // different from Grandparent's

public Parent( int i ){
       super( i+1 ); // calls Grandparent constructor
} // end Parent constructor

public void display(){
       System.out.println("Parent display "+data);
} // end display method

} //end Parent class

public class Child extends Parent{

protected int data; // different from Parent's

public Child( int i ){
       super( i+1 ); // calls Parent constructor
       data = i;
} // end Child constructor

public void display(){
       System.out.println("Child display" +;
       System.out.println("Parent data = " + 
       System.out.println("Grandparent data= " + 
                    ((Grandparent)this).data );
       // Note: Can't call Grandparent's display()
       //      from here even with casting
} // end display method

} // end Child class

Note:  (Grandparent) in the above example is casting the Child reference to its Grandparent.

In another class and file:

public class TryInheritance

public static void main( String[] args )
       Grandparent g = new Grandparent( 100 );
       Parent p1 = new Parent( 10 );
       Parent p2;
       Child c1 = new Child( 1 );
       Child c2;
       p2 = c1; // example of assigning a subclass obj. to superclass var.
       if( p2 instanceof Child )//always check
           c2 = (Child) p2; 
//NOTE: if you downcast and it isn't an instance,
//        an exception will be thrown
       g.display();// displays "Grandparent display 100"
       p1.display();// displays "Parent display 10"
       p2.display();// displays "Child display 1", etc.
       c1.display();// displays "Child display 1", etc.
} // end main

} // end TryInheritance