Безопасность при работе с null
В Kotlin возможно иметь значение null. Kotlin использует значения null, когда что-то отсутствует или ещё не задано. Вы уже видели пример того, как Kotlin возвращает значение null, в главе «Коллекции», когда пытались получить доступ к паре «ключ-значение» с ключом, которого нет в карте. Хотя использовать значения null таким образом удобно, могут возникнуть проблемы, если ваш код не готов их обрабатывать.
Чтобы предотвратить проблемы со значениями null в ваших программах, в Kotlin предусмотрена безопасность при работе с null. Она позволяет выявлять потенциальные проблемы со значениями null во время компиляции, а не во время выполнения.
Безопасность при работе с null — это сочетание возможностей, которые позволяют:
Явно указывать, когда в программе разрешены значения
null.Проверять наличие значений
null.Безопасно обращаться к свойствам и функциям, которые могут содержать значения
null.Задавать действия, которые нужно выполнить при обнаружении значений
null.
Типы, допускающие null
Kotlin поддерживает типы, допускающие null, которые позволяют объявленному типу содержать значения null. По умолчанию типу не разрешено принимать значения null. Типы, допускающие null, объявляются добавлением ? после объявления типа.
Например:
fun main() {
// neverNull has String type
var neverNull: String = "This can't be null"
// Throws a compiler error
neverNull = null
// nullable has nullable String type
var nullable: String? = "You can keep a null here"
// This is OK
nullable = null
// By default, null values aren't accepted
var inferredNonNull = "The compiler assumes non-nullable"
// Throws a compiler error
inferredNonNull = null
// notNull doesn't accept null values
fun strLength(notNull: String): Int {
return notNull.length
}
println(strLength(neverNull)) // 18
println(strLength(nullable)) // Throws a compiler error
}
Проверка значений null
Наличие значений null можно проверять в условных выражениях. В следующем примере функция describeString() содержит инструкцию if, которая проверяет, что maybeString не равно null и что её length больше нуля:
fun describeString(maybeString: String?): String {
if (maybeString != null && maybeString.length > 0) {
return "String of length ${maybeString.length}"
} else {
return "Empty or null string"
}
}
fun main() {
val nullString: String? = null
println(describeString(nullString))
// Empty or null string
}
Безопасные вызовы
Чтобы безопасно обращаться к свойствам объекта, который может содержать значение null, используйте оператор безопасного вызова ?.. Оператор безопасного вызова возвращает null, если объект или одно из его свойств, к которым выполняется обращение, имеет значение null. Это полезно, если вы хотите избежать ошибок в коде, вызванных наличием значений null.
В следующем примере функция lengthString() использует безопасный вызов, чтобы вернуть длину строки или null:
fun lengthString(maybeString: String?): Int? = maybeString?.length
fun main() {
val nullString: String? = null
println(lengthString(nullString))
// null
}
Оператор безопасного вызова также можно использовать для безопасного вызова функции-расширения или функции-члена. В этом случае перед вызовом функции выполняется проверка на null. Если проверка обнаруживает значение null, вызов пропускается и возвращается null.
В следующем примере nullString имеет значение null, поэтому вызов .uppercase() пропускается и возвращается null:
fun main() {
val nullString: String? = null
println(nullString?.uppercase())
// null
}
Оператор Элвиса
Если обнаружено значение null, можно задать значение по умолчанию, которое будет возвращено, используя оператор Элвиса ?:.
Слева от оператора Элвиса укажите, что нужно проверить на значение null. Справа от оператора Элвиса укажите, что нужно вернуть, если обнаружено значение null.
В следующем примере nullString имеет значение null, поэтому безопасный вызов для обращения к свойству length возвращает значение null. В результате оператор Элвиса возвращает 0:
fun main() {
val nullString: String? = null
println(nullString?.length ?: 0)
// 0
}
Подробнее о безопасности при работе с null в Kotlin см. в разделе «Безопасность при работе с null».
Практика
Упражнение
У вас есть функция employeeById, которая предоставляет доступ к базе данных сотрудников компании. К сожалению, эта функция возвращает значение типа Employee?, поэтому результат может быть null. Ваша задача — написать функцию, которая возвращает зарплату сотрудника, если указан его id, или 0, если сотрудника нет в базе данных.
data class Employee (val name: String, var salary: Int)
fun employeeById(id: Int) = when(id) {
1 -> Employee("Mary", 20)
2 -> null
3 -> Employee("John", 21)
4 -> Employee("Ann", 23)
else -> null
}
fun salaryById(id: Int) = // Write your code here
fun main() {
println((1..5).sumOf { id -> salaryById(id) })
}
Что дальше?
Поздравляем! Вы завершили вводный тур. Теперь углубите свои знания Kotlin с помощью нашего тура среднего уровня:
© 2010–2026 JetBrains s.r.o. and Kotlin Programming Language contributors
Licensed under the Apache License, Version 2.0.
https://kotlinlang.org/docs/kotlin-tour-null-safety.html