chapter eleven

11 Generics

 

This chapter covers

  • Declaring generic functions and classes
  • Type erasure and reified type parameters
  • Declaration-site and use-site variance
  • Type aliases

You’ve already seen a few code examples that use generics in this book. The basic concepts of declaring and using generic classes and functions in Kotlin are similar to Java, so the earlier examples should have been clear without a detailed explanation. In this chapter, we’ll return to some of the examples and look at them in more detail.

We’ll then go deeper into the topic of generics and explore new concepts introduced in Kotlin, such as reified type parameters and declaration-site variance. These concepts may be novel to you, but don’t worry; the chapter covers them thoroughly.

Reified type parameters allow you to refer at runtime to the specific types used as type arguments in an inline function call. (For normal classes or functions, this isn’t possible, because type arguments are erased at runtime.)

Declaration-site variance lets you specify whether a generic type with a type argument is a subtype or a supertype of another generic type with the same base type and a different type argument. For example, it regulates whether it’s possible to pass arguments of type List<Int> to functions expecting List<Any>.

Use-site variance achieves the same goal for a specific use of a generic type and therefore accomplishes the same task as Java’s wildcards.

11.1 Creating types with type arguments: Generic type parameters

11.1.1 Functions and properties that work with generic types

11.1.2 Generic classes are declared with the angle bracket syntax

11.1.3 Restricting the type a generic class or function can use: Type parameter constraints

11.1.4 Excluding nullable type arguments by explicitly marking type parameters as non-null

11.2 Generics at runtime: erased and reified type parameters

11.2.1 Limitations to finding type information of a generic class at runtime: type checks and casts

11.2.2 Functions with reified type parameters can refer to actual type arguments at runtime

11.2.3 Avoiding java.lang.Class parameters by replacing class references with reified type parameters

11.2.4 Declaring accessors with reified type parameters

11.2.5 Reified type parameters come with restrictions

11.3 Variance describes the subtyping relationship between generic arguments

11.3.1 Variance determines whether it is safe to pass an argument to a function

11.3.2 Understanding the differences between classes, types, and subtypes

11.3.3 Covariance preserves the subtyping relation