Kotlin Non-Null Assertion
The non-null assertion operator !! tells Kotlin: "I know this value is not null — trust me." It converts a nullable type to a non-nullable type. If the value actually is null at runtime, Kotlin throws a NullPointerException.
How !! Works
val name: String? = "Alice"
val length = name!!.length // treat name as non-null, access .length
println(length) // 6
name!!
│
└── Is name null?
│
├── NO → unwrap and use as String → access .length → OK
└── YES → throw NullPointerException immediately
What Happens When It Is Null
val value: String? = null
val result = value!!.uppercase()
// Throws: NullPointerException: value!! cannot be nullWhen to Use !!
Use !! only when you are absolutely certain the value is not null and the type system does not recognize it yet — for example, when working with Java interop or platform types. In pure Kotlin code, prefer safe calls (?.) or Elvis (?:) instead.
┌─────────────────────────────────────────────────────┐
│ !! is appropriate when: │
│ - You are calling Java code that returns nullable │
│ but you know it never returns null at that point │
│ - You have already validated the value elsewhere │
│ but the type system cannot see that validation │
│ │
│ !! is NOT appropriate when: │
│ - You are just being lazy about null handling │
│ - You are unsure whether the value is null │
│ - A safe call or Elvis can do the job │
└─────────────────────────────────────────────────────┘
Safe Alternatives
val email: String? = getEmailFromServer()
// Risky — crashes if null
val domain = email!!.substringAfter("@")
// Safe — returns null if email is null
val domain = email?.substringAfter("@")
// Safe with fallback
val domain = email?.substringAfter("@") ?: "unknown.com"!! vs Safe Call Comparison
Scenario │ ?. │ !!
──────────────────┼──────────────┼──────────────────────
Value is not null │ works fine │ works fine
Value is null │ returns null │ throws NullPointerException
Error at │ never │ runtime
Recommended? │ yes │ only when certain
Platform Types (Java Interop)
When Kotlin calls Java code, the return type may be a platform type (neither nullable nor non-nullable). In this case, Kotlin cannot enforce null safety, and !! is sometimes needed:
// Java method: public String getUserName() { return null; }
val name = javaClass.getUserName()!!.uppercase()
// crashes if getUserName() returns null — use carefullyPractical Example: Config Loader
fun loadConfig(key: String): String? {
val config = mapOf("db_host" to "localhost", "db_port" to "5432")
return config[key]
}
fun main() {
// We know "db_host" exists in config, so !! is acceptable here
val host = loadConfig("db_host")!!
println("Connecting to: $host")
// Safer version with fallback
val port = loadConfig("db_port") ?: "3306"
println("Port: $port")
// This will crash — "timeout" key does not exist
// val timeout = loadConfig("timeout")!!
}Output:
Connecting to: localhost
Port: 5432The key rule: use !! sparingly. Every !! in your code is a potential crash waiting to happen if your assumption about the value ever turns out to be wrong.
