super and Constructors
Part of the Object Oriented Programming section of Coddy's Kotlin journey. Lesson 19 of 57.
super.method() calls the superclass's version of a method from inside an override. A subclass can extend the inherited behaviour instead of replacing it:
open class Notification(val text: String) {
open fun render() = "[info] $text"
}
class Reminder(text: String, val minutes: Int) : Notification(text) {
override fun render() = super.render() + " (in $minutes min)"
}Inside main:
println(Notification("backup done").render())
println(Reminder("meeting", 10).render())Output:
[info] backup done
[info] meeting (in 10 min)Every subclass must call a superclass constructor. With a primary constructor, the call is part of the header, : Base(arguments), and the arguments can be computed from the subclass's parameters:
open class Product(val name: String, val price: Int)
class Discounted(name: String, price: Int, val percent: Int) :
Product(name, price * (100 - percent) / 100)Inside main:
val tea = Discounted("tea", 500, 10)
println("${tea.name} ${tea.price} (${tea.percent}% off)")Output:
tea 450 (10% off)Creation runs from the top of the hierarchy down: the superclass's property initializers and init blocks run first, then the subclass's:
open class Base(name: String) {
init { println("Base init for $name") }
}
class Child(name: String) : Base(name.uppercase()) {
init { println("Child init for $name") }
}Inside main:
Child("kit")Output:
Base init for KIT
Child init for kitA class without a primary constructor calls the superclass from each secondary constructor with super(...), or delegates to another of its own constructors with this(...):
open class Shape(val name: String)
class Rect : Shape {
val w: Int
val h: Int
constructor(w: Int, h: Int) : super("rect") {
this.w = w
this.h = h
}
constructor(side: Int) : this(side, side)
}Inside main:
val r = Rect(3)
println("${r.name} ${r.w}x${r.h}")Output:
rect 3x3Because the superclass is set up first, it should not call open members from its constructor or init. The override runs before the subclass's own properties have their values:
open class Base {
init { println("Base sees: ${describe()}") }
open fun describe() = "base"
}
class Child : Base() {
val label = "child"
override fun describe() = "label is $label"
}Inside main:
Child()Output:
Base sees: label is nullChallenge
EasyNotification(text) has an open method render() that returns [info] text. Complete the subclasses: Warning's render() returns [warn] TEXT with the text in capital letters, and Reminder, which also stores minutes, returns the superclass result followed by (in 10 min), using super.
The supplied code reads lines info,text, warn,text or remind,text,10, builds the matching object in one List<Notification> and prints render() for each.
Your code goes in Notification.kt, Warning.kt and Reminder.kt. Main.kt holds the supplied input/output code and cannot be edited.
Try it yourself
fun main() {
// Supplied input/output code: keep it as it is
val input = generateSequence(::readLine).toList()
val notes = mutableListOf<Notification>()
for (line in input) {
val p = line.split(",")
notes.add(when (p[0]) {
"warn" -> Warning(p[1])
"remind" -> Reminder(p[1], p[2].toInt())
else -> Notification(p[1])
})
}
for (n in notes) println(n.render())
}
This lesson includes a short quiz. Start the lesson to answer it and track your progress.
All lessons in Object Oriented Programming
1Classes and Objects
Working With FilesDefining ClassesPrimary Constructorsinit Blocks and ValidationSecondary ConstructorsRecap - Library Card4Inheritance
Open Classes and SubclassesOverriding Memberssuper and ConstructorsAbstract ClassesRecap - Staff Directory2Properties and Encapsulation
Custom AccessorsVisibility ModifiersPrivate Setterslazy and lateinitRecap - Bank Account5Interfaces
Declaring InterfacesDefault MethodsMultiple InterfacesInterfaces as TypesRecap - Payment Methods8Generics
Generic FunctionsGeneric ClassesType ConstraintsVariance With in and outRecap - Priority Queue11Project: Library Management
Books and MembersBorrowing BooksPractice on your own: Kotlin playground