V tomto článku se pomocí příkladů dozvíte o třídě Sealed, o tom, jak jsou vytvořeny a kdy je použít.
Uzavřené třídy se používají, když hodnota může mít pouze jeden z typů z omezené sady (omezené hierarchie).
Než se podíváme na podrobnosti o zapečetěných třídách, prozkoumejme, jaký problém řeší. Vezměme si příklad (převzato z oficiálního webu Kotlin - článek Sealed classes):
class Expr class Const(val value: Int) : Expr class Sum(val left: Expr, val right: Expr) : Expr fun eval(e: Expr): Int = when (e) ( is Const -> e.value is Sum -> eval(e.right) + eval(e.left) else -> throw IllegalArgumentException("Unknown expression") )
Ve výše uvedeném programu má základní třída Expr dvě odvozené třídy Const (představuje číslo) a Sum (představuje součet dvou výrazů). Zde je povinné použít else
větev jako výchozí podmínku ve výrazu.
Nyní, pokud odvodíte novou podtřídu ze Expr
třídy, kompilátor nezjistí nic, protože else
ji zpracovává větev, což může vést k chybám. Bylo by lepší, kdyby kompilátor vydal chybu, když jsme přidali novou podtřídu.
Chcete-li tento problém vyřešit, můžete použít zapečetěnou třídu. Jak již bylo zmíněno, zapečetěná třída omezuje možnost vytváření podtříd. A když ve when
výrazu zpracujete všechny podtřídy zapečetěné třídy , není nutné používat else
větev.
K vytvoření zapečetěné třídy se používá zapečetěný modifikátor. Například,
uzavřená třída Expr
Příklad: Utěsněná třída
Tady je způsob, jak vyřešit výše uvedený problém pomocí zapečetěné třídy:
sealed class Expr class Const(val value: Int) : Expr() class Sum(val left: Expr, val right: Expr) : Expr() object NotANumber : Expr() fun eval(e: Expr): Int = when (e) ( is Const -> e.value is Sum -> eval(e.right) + eval(e.left) NotANumber -> java.lang.Double.NaN )
Jak vidíte, neexistuje žádná else
větev. Pokud odvodíte novou podtřídu ze Expr
třídy, kompilátor si stěžuje, pokud není podtřída zpracována ve when
výrazu.
Několik důležitých poznámek
- Všechny podtřídy zapečetěné třídy musí být deklarovány ve stejném souboru, kde je deklarována zapečetěná třída.
- Uzavřená třída je sama o sobě abstraktní a nelze z ní vytvořit instanci objektů.
- Nelze vytvořit neveřejné konstruktory zapečetěné třídy; jejich konstruktory jsou
private
ve výchozím nastavení.
Rozdíl mezi Enum a Sealed Class
Třída Enum a zapečetěná třída jsou si velmi podobné. Sada hodnot pro typ výčtu je také omezena jako uzavřená třída.
Jediný rozdíl je v tom, že enum může mít pouze jednu instanci, zatímco podtřída uzavřené třídy může mít více instancí.