Kotlin Null Safety Explained: ?, !!, let and Safe Calls

Introduction

One of Kotlinโ€™s biggest advantages over Java is built-in null safety.

If you've written Android apps in Java before, you probably remember how often apps crashed because of a NullPointerException.

Kotlin tries to solve this problem by making nullability part of the type system.

This means the compiler can help prevent many null-related bugs before your code even runs.

In this guide weโ€™ll cover the most important Kotlin null safety tools:

  • Nullable types (?)

  • Safe call operator (?.)

  • Not-null assertion (!!)

  • let with null checks

  • Best practices for Android developers

๐Ÿ‘‰ Korean Tip

์ฝ”ํ‹€๋ฆฐ์˜ ๊ฐ€์žฅ ํฐ ์žฅ์  ์ค‘ ํ•˜๋‚˜๊ฐ€ Null Safety ์ž…๋‹ˆ๋‹ค.

Java์—์„œ ์ž์ฃผ ๋ฐœ์ƒํ–ˆ๋˜ NullPointerException ๋ฌธ์ œ๋ฅผ ์ปดํŒŒ์ผ ๋‹จ๊ณ„์—์„œ ์ค„์—ฌ์ฃผ๋Š” ๊ธฐ๋Šฅ์ž…๋‹ˆ๋‹ค.

What is Null Safety in Kotlin?

In Kotlin, variables are non-null by default.

This means the compiler will not allow you to assign null unless you explicitly say the variable can be nullable.

Example:

val name: String = "Kotlin"

This variable cannot be null.

If you want a variable that can hold null, you must add ?.

val name: String? = null

๐Ÿ‘‰ Korean Tip

?๊ฐ€ ๋ถ™์œผ๋ฉด null์ด ๋“ค์–ด๊ฐˆ ์ˆ˜ ์žˆ๋Š” ๋ณ€์ˆ˜๊ฐ€ ๋ฉ๋‹ˆ๋‹ค.

Safe Call Operator (?.)

The safe call operator allows you to safely access properties of nullable objects.

Example

val name: String? = "Android"
println(name?.length)

If name is null, the expression simply returns null instead of crashing.

๐Ÿ‘‰ Korean Tip

?. ์—ฐ์‚ฐ์ž๋Š” null์ด๋ฉด ์‹คํ–‰ํ•˜์ง€ ์•Š๊ณ  null์„ ๋ฐ˜ํ™˜ํ•ฉ๋‹ˆ๋‹ค.

Equivalent Java-style code would look like this:

if (name != null) {
    println(name.length)
}

The Kotlin version is much cleaner.

Using let for Null Checks

One of the most common patterns in Kotlin is combining safe calls with let.

Example

val name: String? = "Kotlin"

name?.let {
println("Name is $it")
}

This block runs only if the value is not null.

๐Ÿ‘‰ Korean Tip

?.let { } ํŒจํ„ด์€ ์ฝ”ํ‹€๋ฆฐ์—์„œ ๊ฐ€์žฅ ๋งŽ์ด ์‚ฌ์šฉํ•˜๋Š” null ์ฒดํฌ ๋ฐฉ์‹์ž…๋‹ˆ๋‹ค.

The Not-Null Assertion Operator (!!)

Sometimes developers use !! to force a nullable value to be treated as non-null.

Example:

val name: String? = "Kotlin"

println(name!!.length)

If name happens to be null, the app will crash.

๐Ÿ‘‰ Korean Tip

!!๋Š” null์ด ์•„๋‹ˆ๋ผ๊ณ  ๊ฐ•์ œ๋กœ ๋‹จ์ •ํ•˜๋Š” ์—ฐ์‚ฐ์ž์ž…๋‹ˆ๋‹ค.

ํ•˜์ง€๋งŒ null์ด๋ฉด ์•ฑ์ด ๋ฐ”๋กœ crashํ•ฉ๋‹ˆ๋‹ค.

Developer Tip

Avoid using !! whenever possible.

Most experienced Kotlin developers consider frequent use of !! a code smell.

Elvis Operator (?:)

The Elvis operator provides a default value if something is null.

Example:

val name: String? = null

val result = name ?: "Guest"
println(result)

Output

Guest

๐Ÿ‘‰ Korean Tip

?: ๋Š” null์ผ ๊ฒฝ์šฐ ๊ธฐ๋ณธ๊ฐ’์„ ์ œ๊ณตํ•˜๋Š” ์—ฐ์‚ฐ์ž์ž…๋‹ˆ๋‹ค.


Common Null Safety Patterns

Here are some patterns you'll see often in Kotlin code.

Pattern 1: Safe call

user?.email

Pattern 2: let block

user?.let {
sendEmail(it)
}

Pattern 3: Default value

val name = user?.name ?: "Guest"

๐Ÿ‘‰ Korean Tip

์ด ์„ธ ๊ฐ€์ง€ ํŒจํ„ด์€ Android Kotlin ์ฝ”๋“œ์—์„œ ๊ฑฐ์˜ ๋งค์ผ ์‚ฌ์šฉํ•˜๋Š” ํŒจํ„ด์ž…๋‹ˆ๋‹ค.

Common Mistakes Developers Make

Using !! too often

This defeats the purpose of Kotlin null safety.

Example:

val name: String? = null
println(name!!.length)

This will crash.ย 


Forgetting nullable types

Sometimes developers forget to mark variables nullable.

Example:

val name: String = null

This will not compile.

Best Practices for Kotlin Null Safety

Prefer safe calls

user?.email

Use let for scoped logic

user?.let {
sendEmail(it)
}

Use Elvis operator for defaults

val username = user?.name ?: "Guest"

๐Ÿ‘‰ Korean Tip

Kotlin Null Safety์˜ ํ•ต์‹ฌ์€

  • ?.

  • let

  • ?:

์ด ์„ธ ๊ฐ€์ง€๋ฅผ ์ž˜ ํ™œ์šฉํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.


Quick Kotlin Null Safety Cheat Sheet

Feature Example Purpose
Nullable type String? allow null
Safe call ?. avoid crash
let ?.let {} null check
Elvis operator ?: default value
Not-null assertion !! force non-null

FAQ

Why does Kotlin care so much about null?

Because NullPointerException is one of the most common causes of app crashes.

Kotlinโ€™s type system helps prevent these errors.

Should I ever use !!?

Only when you are absolutely sure the value cannot be null.

Even then, many developers prefer safer alternatives.

What is the most common null handling pattern?

This one:

value?.let { }

ย 

ย 

heejin's picture

Language

Get in touch with us

"If you would thoroughly know anything, teach it to other."
- Tryon Edwards -