Sobes.tech
Junior

Welke soorten generieken ken je?

sobes.tech AI

Antwoord van AI

Invarianten, covariante en contravariante.

  • Invariantie: Het type List<A> is geen subtype van List<B> en vice versa, zelfs als A een subtype is van B. Het type blijft precies.
  • Covariantie (out): Staat toe om subtypes te gebruiken. List<A> is een subtype van List<B> als A een subtype is van B. Gebruikt voor outputparameters (teruggegeven waarden).
fun foo(list: List<out Number>) {
    // Kan lezen uit de lijst (Number, Double, Int, etc.)
    val number: Number = list[0]
    // Kan niet toevoegen aan de lijst (het is niet bekend welk type elementen worden verwacht)
    // list.add(1) // Compileerfout
}
  • Contravariantie (in): Staat toe om supertypen te gebruiken. List<B> is een subtype van List<A> als A een subtype is van B. Gebruikt voor invoerparameters (argumenten).
fun foo(comparable: Comparable<in String>) {
    // Argumenten van type String (of zijn supertypen) kunnen worden doorgegeven
    val result = comparable.compareTo("hello")
    // Resultaten van type String kunnen niet worden opgehaald (het is niet bekend welk type resultaat)
    // val str: String = comparable.compareTo("world") // Compileerfout
}

In Kotlin worden deze concepten geïmplementeerd met de annotaties out en in op de typeparameters. In Java worden wildcards (? extends voor covariantie en ? super voor contravariantie) gebruikt.

Type Doel Sleutelwoord (Kotlin) Wildcard (Java) Lezen toegestaan Schrijven toegestaan
Invariant Exacte overeenstemming van het type Nee Nee Ja Ja
Covariante Gebruik van subtypes (producent - "out") out ? extends T Ja Nee
Contravariantie Gebruik van supertypen (consument - "in") in ? super T Nee Ja