Typealias je mechanismus Kotlinu pro vytvoření alternativního názvu existujícího typu. Klíčové slovo typealias umožňuje nahradit složité deklarace typu krátkým a srozumitelným aliasem, aniž by se vytvářel nový typ. Podle dokumentace Kotlinu (2026) typealias zvyšuje čitelnost kódu, zejména v signaturách funkcí s funkčními typy. Typealias činí kód samodokumentujícím, nahrazuje mnohomluvné deklarace srozumitelnými pojmenovanými typy.
Hlavní body
Typealias (alias typu) — deklarace, která zavádí alternativní název pro existující typ. Syntaxe: typealias NovýNázev = ExistujícíTyp. Po deklaraci lze NovýNázev použít všude, kde se očekává ExistujícíTyp — kompilátor je považuje za stejný typ. Na úrovni bytecode typealias nezanechává stopy: všechny informace o aliasu jsou vymazány ve fázi kompilace.
Hlavním cílem typealias je zlepšení čitelnosti kódu. Místo dlouhé signatury fun process(callback: (Result) -> Unit) lze napsat typealias Callback = (Result) -> Unit a používat Callback jako typ parametru. To je užitečné zejména tehdy, když se stejný funkční typ opakuje na více místech kódu: alias slouží jako jednotný bod definice a dokumentuje účel typu.
Typealias nevytváří nový typ — je pouze synonymem. Proměnné typu Callback a (Result) -> Unit jsou plně zaměnitelné. Kompilátor nevyhodí chybu, pokud je do funkce očekávající Callback předána přímo lambda. Tím se typealias liší od inline class (value class), která vytváří nový typ-obálku s kontrolou ve fázi kompilace. Typealias je přejmenování, nikoli obalení.
Nejčastějším scénářem použití typealias v Kotlinu jsou funkční typy. Dlouhé signatury jako (Int, String) -> Boolean nebo (List
// Bez typealias
fun findUsers(
filter: (List<User>) -> List<User>
): List<User>
// S typealias
typealias UserFilter = (List<User>) -> List<User>
fun findUsers(filter: UserFilter): List<User>
// Použití ve třídě
typealias OnClickListener = (View) -> Unit
class Button {
var onClick: OnClickListener = {}
}
V příkladu typealias UserFilter skrývá složitý funkční typ (List
Typealias podporuje generické parametry, což ho činí ještě flexibilnějším. Lze definovat typealias Mapper
// Generický typealias
typealias Mapper<T, R> = (T) -> R
typealias Provider<T> = () -> T
typealias ListTransformer<T> = (List<T>) -> List<T>
fun processNumbers(mapper: Mapper<Int, String>) {
// typ mapperu je (Int) -> String
}
fun main() {
val config: Provider<String> = { "default config" }
val reverse: ListTransformer<Int> = { it.reversed() }
}
Ve výpisu Mapper
Vnořené třídy a dlouhé parametrizované typy — další oblast, kde typealias výrazně zjednodušuje kód. Pokud je třída hluboko v hierarchii vnoření (Outer.Inner.Nested), odkazování na ni plným názvem zahlcuje kód. Typealias tento přístup zkracuje a činí ho čitelnějším. To je důležité zejména pro třídy z knihoven třetích stran s dlouhými názvy.
// Alias pro vnořenou třídu
class NetworkResponse {
class Error(val code: Int, val message: String)
}
typealias NetworkError = NetworkResponse.Error
// Alias pro dlouhý typ knihovny
typealias UserId = Long
typealias JsonMap = Map<String, Any?>
fun process(error: NetworkError) {
println("${error.code}: ${error.message}")
}
fun parseJson(data: JsonMap): UserId {
return data["id"] as? Long ?: 0L
}
V příkladu NetworkError — alias pro vnořenou třídu NetworkResponse.Error. Při importu typealias lze NetworkError používat jako běžný typ, aniž by se odhalovala hierarchie vnoření. JsonMap dokumentuje, že mapa představuje JSON objekt. UserId vysvětluje účel Long v konkrétním kontextu — čtenář okamžitě chápe, že se jedná o identifikátor uživatele, nikoli libovolné číslo. Typealias však nechrání před předáním obyčejného Long tam, kde se očekává UserId — k tomu je potřeba value class.
Typealias a inline class (value class) řeší různé úkoly, i když oba zavádějí nový název pro typ. Typealias je jen synonymum: proměnná typu UserId = Long přijímá jakýkoli Long bez kontroly. Inline class obaluje hodnotu do nového typu, který je kontrolován ve fázi kompilace: předání obyčejného Long tam, kde se očekává inline class UserId, není možné bez explicitní konverze.
| Vlastnost | Typealias | Inline class |
|---|---|---|
| Nový typ | Ne — synonymum originálu | Ano — nový typ s kontrolami |
| Výkon | Žádný — zcela vymazán | Žádný — obálka odstraněna v bytecode |
| Dědičnost | Ne | Ne (final class) |
| Vlastní metody | Ne | Ano — lze deklarovat funkce |
| Bezpečnost typů | Ne — zaměnitelný s originálem | Ano — kompilátor rozlišuje typy |
Tabulka ukazuje rozdíl mezi oběma mechanismy. Typealias je vhodný pro krátké názvy a dokumentaci kódu, když není vyžadována striktní typizace. Inline class přes klíčové slovo value class (dříve inline class) je potřeba, když je důležité rozlišovat sémanticky odlišné hodnoty stejného primitivního typu. Například UserId a OrderId jsou oba Long, ale předání jednoho tam, kde se očekává druhý, je logická chyba, které value class zabraňuje ve fázi kompilace.
Často kladené otázky
Import alias (import com.example.LongName as Short) funguje na úrovni importu — zkracuje název pouze v aktuálním souboru. Typealias deklaruje globální alias dostupný v celém projektu po importu.
Ano, typealias podporuje rekurzivní definice pro funkční typy, ale s opatrností: typealias Rec
Ne, typealias je zcela vymazán ve fázi kompilace. V bytecode a runtime se používá původní typ bez jakékoli obálky. Výkon je identický s přímým použitím původního typu.
Typealias může odkazovat na jiný typealias — to se nazývá řetězec aliasů. Hloubka řetězce formálně není omezena, ale pro čitelnost se doporučuje maximálně 2–3 úrovně. Kompilátor řetězec plně rozvine ve fázi analýzy.
Ne, typealias je deklarace nejvyšší úrovně nebo člen třídy/objektu. Uvnitř funkcí nelze typealias deklarovat. Pro lokální zkrácení typů použijte import alias uvnitř souboru nebo vyčleňte typealias na úroveň modulu.
Shrnutí
Vyvineme mobilní aplikaci na klíč
IT Sectr vytváří aplikace pro iOS a Android pro startupy a podniky od roku 2017. Poradíme vám a navrhneme nejlepší řešení.
Přečtěte si také