1.1.50.6. fejezet, Osztályok

Konstruktor

class Person constructor(firstName: String) { /*...*/ }
 
class Person(firstName: String) { /*...*/ }

Az elsődleges konstruktorban nem szerepelhetnek inicializáláson kívül más kódrészletek. Ha mégis szükségünk lenne ilyen műveletekre, használnunk kell az init blokkokat, amelyek a példányositás során deklarálásuk sorredjében végrehajtódnak.

class InitOrderDemo(name: String) {
    val firstProperty = "First property: $name".also(::println)
 
    init {
        println("First initializer block that prints $name")
    }
 
    val secondProperty = "Second property: ${name.length}".also(::println)
 
    init {
        println("Second initializer block that prints ${name.length}")
    }
}

A konstruktor definiálja a tulajdonságokat, alapértelmezett értékek is megadhatók:

class Person(val firstName: String, val lastName: String, var isEmployed: Boolean = true)

Másodlagos konstruktor

class Person(val pets: MutableList<Pet> = mutableListOf())
 
class Pet {
    constructor(owner: Person) {
        owner.pets.add(this) // adds this pet to the list of its owner's pets
    }
}

Ha annotáció vagy láthatósági jelölés szerepel a konstruktor előtt, akkor így készítsük:

class Customer public @Inject constructor(name: String) { /*...*/ }

Minden másodlagos konstruktornak meg kell hívnia az elsődleges konstruktor a következő módon:

class Person(val name: String) {
    val children: MutableList<Person> = mutableListOf()
    constructor(name: String, parent: Person) : this(name) {
        parent.children.add(this)
    }
}

A másodlagos konstruktor paramétereiből nem lesznek osztály tulajdonságok.

Ha mégsincs elsődleges konstruktor, akkor a delegáció mégis implicit megtörténik és az inicializáló blokkok sorban meghívódnak.

class Constructors {
    init {
        println("Init block")
    }
 
    constructor(i: Int) {
        println("Constructor $i")
    }
}

Példányosítás

Osztály példányosítása ugyanúgy néz ki mint egy függvény hívás, kotlin-ban nincs new kulcsszó:

val invoice = Invoice()
 
val customer = Customer("Joe Smith")

Absztrakt osztályok

abstract class Polygon {
    abstract fun draw()
}
 
class Rectangle : Polygon() {
    override fun draw() {
        // draw the rectangle
    }
}

Egy open metódust felülírhatunk egy absztrakt metódussal:

open class Polygon {
    open fun draw() {
        // some default polygon drawing method
    }
}
 
abstract class WildShape : Polygon() {
    // Classes that inherit WildShape need to provide their own
    // draw method instead of using the default on Polygon
    abstract override fun draw()
}