Properties, lazy & lateinit Quiz

KOTLIN › Language Idioms

Which property can be declared with lazy { ... }?

Answer: A val, since lazy is a read-only delegate only

lazy() returns a Lazy<T> delegate that only supplies getValue, so it can back a val (read-only). There is no setValue, so it cannot be used with var.

What happens to a const val reference after compilation?

Answer: Its literal value is inlined directly at each usage site

const val is a compile-time constant whose value is inlined at every reference, so no getter is called and access is essentially free.

Which declaration is INVALID for lateinit?

Answer: lateinit var count: Int

lateinit cannot be used with primitive types like Int; it requires a non-null reference type because it relies on a null sentinel to detect the uninitialized state.

Accessing a lateinit var before it is assigned throws what?

Answer: kotlin.UninitializedPropertyAccessException

Reading an unassigned lateinit property throws kotlin.UninitializedPropertyAccessException, a dedicated exception distinct from NPE.

Which property does NOT get a backing field generated?

Answer: val area: Int get() = width * height

A property with only a custom getter that never references field is fully computed, so the compiler generates no backing field. The others use field or default accessors, which require storage.

What is the default thread-safety mode of lazy()?

Answer: LazyThreadSafetyMode.SYNCHRONIZED, with locking by default

Without an argument, lazy() uses SYNCHRONIZED, which locks so the initializer runs at most once even under concurrent access.

Inside a custom setter, what does the field keyword refer to?

Answer: The property's backing field that stores the value

field is the special identifier for the property's backing field, available only inside accessors; assigning field = value stores the value without recursively invoking the setter.

You need a non-null Int property assigned after construction, but lateinit rejects primitives. What is the idiomatic Kotlin solution?

Answer: Use by Delegates.notNull<Int>() from kotlin.properties

Delegates.notNull() supplies a delegate that works for primitives and throws if read before assignment, filling the gap that lateinit leaves because lateinit cannot be applied to primitive types.

Where is a const val allowed to be declared?

Answer: At top level, in an object, or in a companion object

const requires a value known at compile time with no per-instance storage, so it is restricted to top-level declarations, objects, or companion objects and cannot be an instance member or a local.

When is LazyThreadSafetyMode.NONE the appropriate choice for lazy()?

Answer: When access stays on one thread and you want no locking overhead

NONE removes all synchronization for the cheapest possible access, which is safe only when the property is touched from one thread; concurrent access under NONE is undefined behavior.

A val has a custom getter and no backing field and is read twice in a row. What is guaranteed?

Answer: The getter runs on every read, so each access can differ

A computed property runs its getter on every access and caches nothing, so a val such as get() = System.currentTimeMillis() can return a fresh value each time it is read.

Given private val _items = mutableListOf<T>(); val items: List<T> get() = _items, what does external code receive when it reads items?

Answer: A read-only List view of the same underlying mutable list

Callers see the List interface, which exposes no mutators, while the same underlying instance stays mutable internally; it is a view rather than a copy, so internal mutations are visible through items.

For the declaration var token: String = ""; private set, which statement is true?

Answer: External code can read it, but only the declaring class can assign it

private set narrows only the setter's visibility; the getter remains public, so outside code can read token while only the declaring class is allowed to write to it.

What is the correct way to check a lateinit property's initialization state from inside its class?

Answer: Use a property reference: this::name.isInitialized

isInitialized is exposed only through a property reference such as this::name.isInitialized; it returns true once assigned and is available only where the property itself is accessible.

Back to Properties, lazy & lateinit