Properties
Kotlin is a modern, concise language where properties replace Java's fields and getters/setters — you can add custom accessors, computed values, and deferred initialisation with very little code.
Learn Properties in our free Kotlin course — a beginner-friendly interactive lesson with worked examples, a practice exercise and a quick reference.
Part of the free Kotlin course at LearnCodingFast — hands-on lessons with examples you run in your browser, plus practice exercises and a quick quiz.
By the end of this lesson you'll write custom getters and setters, computed properties, and use lateinit and by lazy .
What You'll Learn in This Lesson
1️⃣ Custom Getters and Setters
A property can define a custom get() that computes its value, or a custom set(value) that validates or transforms what's stored. Inside a setter, the keyword field refers to the backing storage so you avoid infinite recursion.
fahrenheit has no stored value — it's recomputed from celsius every time. The label setter cleans up input before storing it in field .
2️⃣ lateinit and by lazy
lateinit var lets you declare a non-null property you'll assign later — handy when the value isn't ready at construction. by lazy computes a value once, on first access, then caches it for all future reads.
Notice the loading message prints only once, even though settings is read twice — that's lazy caching the first result.
Your turn. Replace the TODO , then run and compare.
Combine a custom setter (to capitalise) with a computed property (the greeting).
📋 Quick Reference — Properties
Practice quiz
What is a computed property?
- A property cached after first access
- A property with no stored value that calculates via a custom getter
- A property that can never change
- A property stored in a database
Answer: A property with no stored value that calculates via a custom getter. A computed property has only a custom getter and recalculates each time it is read.
Inside a custom setter, what does the field keyword refer to?
- The property's backing field, the actual stored value
- The class itself
- A new local variable
- The getter function
Answer: The property's backing field, the actual stored value. field is the backing field; using it avoids the infinite recursion of writing the property by name.
Why assign to field rather than the property name inside its own setter?
- It is just a style preference
- The property name is read-only there
- Writing the property name calls the setter again, causing infinite recursion
- field is faster to type
Answer: Writing the property name calls the setter again, causing infinite recursion. Assigning name = value inside name's setter calls the setter forever; field writes storage directly.
When is a property declared with lateinit allowed?
- Only with val
- Only with primitive types
- With var and non-primitive types
- With any type at all
Answer: With var and non-primitive types. lateinit works only with var and non-primitive types.
What happens if you read a lateinit property before assigning it?
- It returns null
- It returns a default value
- It silently does nothing
- It throws an UninitializedPropertyAccessException
Answer: It throws an UninitializedPropertyAccessException. Reading an unassigned lateinit throws UninitializedPropertyAccessException.
How does a by lazy property behave?
- It recomputes on every read
- It computes once on first access, then caches the result
- It must be set in the constructor
- It can only hold nullable values
Answer: It computes once on first access, then caches the result. lazy defers computation to first access and caches the value for later reads.
How does a computed property differ from a by lazy property?
- They are identical
- Computed caches once; lazy recomputes each time
- Computed recomputes each read; lazy computes once and caches
- Only lazy can have a getter
Answer: Computed recomputes each read; lazy computes once and caches. Computed properties recalculate every read; lazy computes at most once and caches.
Which property kind is best for a value derived from changing state that must always be current?
- by lazy
- A computed property
- lateinit
- A const
Answer: A computed property. A computed property always reflects current state because it recalculates on each read.
What is a good use case for lateinit?
- A constant known at compile time
- A non-null var initialized after construction, e.g. in a setup method
- A read-only val
- Caching an expensive computation
Answer: A non-null var initialized after construction, e.g. in a setup method. lateinit suits non-null vars set after construction, like dependency injection or setup.
What is the purpose of a custom setter that validates input?
- To make the property read-only
- To transform or check values before storing them in field
- To cache the value
- To defer initialization
Answer: To transform or check values before storing them in field. A custom setter can clean, validate, or transform the value before writing it to field.