liveBook · Manning

Extension property

As explained in Kotlin in Action, 2E

An extension property is a Kotlin property that provides property-like access to an existing type without storing state in that type.

An extension property adds property-style access to an existing type without modifying its source or storing state in its instances. It resembles a regular property with a receiver type, but it must define custom accessors because no backing field exists. section 3.3.5 section 3.7

Listing 3.8 Declaring an extension property
val String.lastChar: Char
   get() = this.get(length - 1)

A read-only extension property computes the last character of a String while preserving property syntax. section 3.3.5

Use extension properties with these constraints and conventions:

  • Define a getter explicitly; initializers and default accessors are unavailable because the extension has no backing field. section 3.3.5
  • Declare a mutable extension property when the receiver already exposes mutable state, as with StringBuilder. section 3.3.5
  • Call extensions with ordinary property syntax in Kotlin, but invoke generated getters and setters explicitly from Java. section 3.3.5
  • Use extensions on primitive receivers to create concise domain-specific values such as days, hours, and fortnights. section 13.4.2

Mutable last-character access

var StringBuilder.lastChar: Char get() = this.get(length - 1) set(value) { this.setCharAt(length - 1, value) } fun main() { val sb = StringBuilder("Kotlin?") println(sb.lastChar) sb.lastChar = '!' println(sb) } section 3.3.5

Listing 13.21 Defining a date manipulation DSL
import kotlin.time.DurationUnit
 
val Int.days: Duration
    get() = this.toDuration(DurationUnit.DAYS)    #1
 
val Int.hours: Duration
    get() = this.toDuration(DurationUnit.HOURS)   #2

Primitive receivers can expose readable measurement syntax; Int.days and Int.hours convert numeric values into Duration values. section 13.4.2

Generic accessors can also be inline and reified: a canonical extension property uses T::class.java to expose the canonical Java class name through property syntax. section 11.2.4

How Kotlin in Action, 2E covers it

How deep it goes
Explains receivers, custom accessors, absent backing fields, mutability, Java calls, and reified accessors through examples.
Examples
Uses String.lastChar, mutable StringBuilder.lastChar, generic canonical, and Int-based date-duration properties.
What it assumes
Assumes Kotlin property, getter, setter, and extension-function syntax while demonstrating these mechanisms through staged examples.
What you can do after
Build it from scratch using custom getters and setters for concise, state-free APIs on existing Kotlin or Java types.
How it connects
Connects extension functions, properties, custom accessors, backing fields, Java interoperability, generics, reified type parameters, and DSLs.

Related concepts

This explainer was generated by Manning's knowledge graph from the text of Kotlin in Action, 2E. The section links point to the parts of the book it draws on.