CodeBlanks Logo Icon CodeBlanks

Summary - Inheritance

Combine open, override and abstract to write a shape hierarchy.

Summary - Inheritance

In this group you learned inheritable classes with open, method redefinition with override, base behavior with super, contracts with abstract and interface implementation with interface.

Now you will combine them: an abstract base class, concrete subclasses inheriting it, and an implemented interface, forming a shape hierarchy. This structure is the backbone of Kotlin object-oriented programming. Later, sealed classes and generics will build on this foundation.

Practice Combine the Shape hierarchy

Define an abstract class named Shape with a primary constructor taking val name: String. Add an abstract fun area(): Double method. Define a subclass named Square with a primary constructor taking name: String, val side: Double that inherits from Shape(name); its override fun area(): Double returns side * side. Define another subclass named Triangle with a primary constructor taking name: String, val base: Double, val height: Double that inherits from Shape(name); its override fun area(): Double returns 0.5 * base * height. In main create an instance of each subclass and print name and area.

Starter code

Main.kt
// Shape abstract class
// abstract area method signature
// Square subclass, name and side
// Triangle subclass, name, base, height
// create two instances in main, print name and area

Sample solution

Main.kt
abstract class Shape(val name: String) {
    abstract fun area(): Double
}

class Square(name: String, val side: Double) : Shape(name) {
    override fun area(): Double = side * side
}

class Triangle(name: String, val base: Double, val height: Double) : Shape(name) {
    override fun area(): Double = 0.5 * base * height
}

fun main() {
    val s = Square("Square", 4.0)
    val t = Triangle("Triangle", 6.0, 3.0)
    println("${s.name}: ${s.area()}")
    println("${t.name}: ${t.area()}")
}

Expected output

Square: 16.0
Triangle: 9.0

What comes next?

You learned inheritance and interfaces. In the next groups you will explore data classes, copying with copy and closed hierarchies with sealed classes.

This group combined open, override, super, abstract and interface. These are the foundations of Kotlin inheritance. Next you will see the methods that data classes generate automatically, such as equals, hashCode and toString.

Practice The Paid interface and the Contractor class

Define an interface named Paid with a method fun pay(): Double. Define an open class named Employee with a primary constructor taking val name: String, val hourlyRate: Double and an open fun hours() = 40 method. Define a subclass named Contractor that inherits from Employee(name, hourlyRate), implements the Paid interface, and provides override fun hours() = 30 and override fun pay(): Double returning hourlyRate * hours(). In main create a Contractor instance and print name and pay.

Starter code

Main.kt
// Paid interface
// fun pay(): Double signature
// Employee open class, name and hourlyRate
// Contractor subclass, implements Employee and Paid
// override hours and pay; instantiate and print in main

Sample solution

Main.kt
interface Paid {
    fun pay(): Double
}

open class Employee(val name: String, val hourlyRate: Double) {
    open fun hours() = 40
}

class Contractor(name: String, hourlyRate: Double) : Employee(name, hourlyRate), Paid {
    override fun hours() = 30
    override fun pay(): Double {
        return hourlyRate * hours()
    }
}

fun main() {
    val c = Contractor("Alex", 50.0)
    println("${c.name} pay: ${c.pay()}")
}

Expected output

Alex pay: 1500.0

Questions and answers

Review the lesson questions together with their answers. To test yourself, solve the lesson interactively.

1 Which modifier does a subclass use to redefine an open method of its base class?

  • override Correct answer
  • open
  • abstract
  • final

Explanation: The override modifier marks a redefinition.

2 Complete the interface implementation

Question
class Triangle : ____ {
    override fun area() = 0.5 * base * height
}
Answer
class Triangle : Shape {
    override fun area() = 0.5 * base * height
}

Explanation: An abstract class is inherited with :.

All lessons in Intermediate