extends and super: building on a class
Inheritance lets one class start from another. class Dog extends Animal means a Dog is an Animal: it gets every public and protected field and method of Animal for free and can add its own. Animal is the superclass (parent), Dog the subclass (child). Java allows exactly one superclass per class; a class that names none extends Object.
public class Main {
public static void main(String[] args) {
Dog rex = new Dog("Rex");
rex.eat(); // inherited from Animal
rex.bark(); // defined in Dog
System.out.println(rex.name + " is an Animal? " + (rex instanceof Animal));
}
}
class Animal {
protected String name;
Animal(String name) {
this.name = name;
}
void eat() {
System.out.println(name + " is eating");
}
}
class Dog extends Animal {
Dog(String name) {
super(name); // run Animal's constructor first
}
void bark() {
System.out.println(name + " says woof");
}
}Rex is eating
Rex says woof
Rex is an Animal? trueAdd a Cat subclass with a meow() method and call both eat() and meow() on it.
Constructors run parent-first
Constructors are not inherited. Every constructor must first run a constructor of its parent, written as super(...) on its first line. If you leave it out, the compiler silently inserts super() — the no-argument version. So an object is built from the top of the hierarchy down: Object, then the parent, then the child.
public class Main {
public static void main(String[] args) {
new Puppy();
}
}
class Animal {
Animal() { System.out.println("1. Animal constructor"); }
}
class Dog extends Animal {
Dog() { System.out.println("2. Dog constructor"); } // implicit super()
}
class Puppy extends Dog {
Puppy() { System.out.println("3. Puppy constructor"); } // implicit super()
}1. Animal constructor
2. Dog constructor
3. Puppy constructorEven though main only asks for a Puppy, all three constructors run, parent first.
constructor Animal in class Animal cannot be applied to given types
public class Main {
public static void main(String[] args) {
System.out.println(new Dog().name);
}
}
class Animal {
String name;
Animal(String name) { this.name = name; }
}
class Dog extends Animal {
Dog() {
System.out.println("making a dog");
}
}Main.java:13: error: constructor Animal in class Animal cannot be applied to given types;
Dog() {
^
required: String
found: no arguments
reason: actual and formal argument lists differ in length
1 errorDog() has no explicit super(...), so the compiler inserted super(). But Animal only has a constructor that takes a String — declaring any constructor removes the free no-argument one. There is nothing for super() to call.
Call the constructor that exists, as the very first statement: super("Rex"); — or pass a name into Dog's constructor and forward it.
public class Main {
public static void main(String[] args) {
System.out.println(new Dog("Rex").name);
}
}
class Animal {
String name;
Animal(String name) { this.name = name; }
}
class Dog extends Animal {
Dog(String name) {
super(name);
System.out.println("making a dog");
}
}private members of the parent exist inside the child object but the child's code cannot touch them — use the parent's public methods, or make the member protected if subclasses genuinely need it. Access modifiers are covered in Module 05 · Classes & Objects.