Do the same precedence rules apply to extension PROPERTIES versus member properties? What happens if you declare an extension property whose name matches an existing member property?
answer
- Member property beats same-name extension property
- Extension properties have NO backing field
- Sugar over get()/set() with hidden receiver
- Can't add storage or a setter to a member
- Statically dispatched, shadowed by member
basics
~10 sYes — the same rule holds. A member property always wins over a same-named extension property. The extension property is shadowed and never read or written through the instance.
solid answer
~40 sExtension properties obey the identical precedence rule: on a name collision with a member property, the **member wins** and the extension property is **shadowed**. Like extension functions, extension properties are **statically dispatched** and have **no backing field** — they are pure syntactic sugar over a getter (and optional setter) that take the receiver as a hidden parameter. So an extension property can't store state and can't override a real member property. The shadowing is by **simple name**: `instance.prop` resolves to the member's accessor. The IDE warns that the extension property is shadowed. Because extension properties compile to `getProp(receiver)` / `setProp(receiver, value)` style accessors, there is no virtual lookup and no field; the member's genuine field/accessor always takes precedence for the matching name.
code
kotlin · 9 linesclass User(val name: String) {
val displayName: String get() = name.uppercase()
}
val User.displayName: String get() = "ext" // shadowed
fun main() {
println(User("ann").displayName) // "ANN" — member wins
}go deeper
Knows extension properties exist and that the member wins on a name clash.
Explains that extension properties have no backing field and are shadowed by members.
Connects field-less static accessors to why no override/augment is possible, including the val/var setter case.
Reasons about API design: using extension properties for derived views only, and why field-less accessors are the right boundary for safe, non-hijacking extension.
## Extension properties recap An **extension property** adds a property-like accessor to a type from outside: ```kotlin val String.firstChar: Char get() = this[0] "abc".firstChar // 'a' ``` Crucially, an extension property has **no backing field** — you must provide a custom `get()` (and `set()` if mutable). It is sugar over a function that takes the receiver as a hidden parameter. It does **not** add storage to the type. ## Same precedence rule If a member property and an extension property share a **name**, the **member wins**, exactly like functions: ```kotlin class User(val name: String) { val displayName: String get() = name.uppercase() } val User.displayName: String get() = "ext" fun main() { println(User("ann").displayName) // "ANN" — member property wins } ``` The extension property compiles but is **shadowed**; `user.displayName` resolves to the member accessor. The IDE flags it as shadowed by a member. ## Why it's consistent with functions Properties are accessor pairs (`get`/`set`) under the hood. An extension property is **statically dispatched** and **field-less**, so: - it can't override a member (no virtual mechanism), - it can't shadow the member's storage, - the member's accessors are authoritative for that name. ## Mutability detail If the member is a `val` but you write a `var` extension with a `set`, the extension setter is still **shadowed** — you cannot use it to 'add a setter' to the member. The member's read-only contract stands. ## What still works An extension property with a **non-colliding name** is freely usable. Extension properties are great for **derived/computed** views (no state), but they never replace or augment an existing member property of the same name.
- Can an extension property hold state to back the member it shadows?No. Extension properties have no backing field, so they can store nothing. They're only computed accessors; they can never carry state for any property, let alone shadow a member's field.
- If the member is a `val`, can a `var` extension property of the same name 'add' a setter?No. The extension is shadowed entirely; the member's read-only contract holds and the extension setter is unreachable through the instance.
saying these in an interview costs you the question
- Saying extension properties can have a backing field
- Claiming an extension property overrides or augments a member
- Thinking you can add a setter to a member via extension
- Believing properties follow different precedence than functions
- Assuming the extension's get() runs sometimes for the same name