Функции-расширения
В этой главе вы познакомитесь со специальными функциями Kotlin, которые делают код более лаконичным и понятным. Узнайте, как они помогают применять эффективные шаблоны проектирования и выводить ваши проекты на новый уровень.
Функции-расширения
При разработке программного обеспечения часто требуется изменить поведение программы, не меняя исходный код. Например, может понадобиться добавить дополнительные возможности классу из сторонней библиотеки.
Для этого можно расширить класс с помощью функций-расширений. Вызывайте функции-расширения так же, как функции-члены класса, используя точку ..
Прежде чем перейти к полному синтаксису функций-расширений, нужно понять, что такое получатель. Получатель — это объект, для которого вызывается функция. Другими словами, получатель — это тот, с кем или в отношении чего происходит обмен информацией.
В этом примере функция main() вызывает функцию .first(), чтобы вернуть первый элемент списка. Функция .first() вызывается для переменной readOnlyShapes, поэтому переменная readOnlyShapes является получателем.
Чтобы создать функцию-расширение, укажите имя класса, который хотите расширить, затем . и имя своей функции. Продолжите объявление функции, указав ее параметры и тип возвращаемого значения.
Например:
fun String.bold(): String = "<b>$this</b>"
fun main() {
// "hello" is the receiver
println("hello".bold())
// <b>hello</b>
}
В этом примере:
String— расширяемый класс.bold— имя функции-расширения.Тип возвращаемого значения функции-расширения
.bold()—String."hello", экземплярString, используется как получатель.Доступ к получателю внутри тела функции осуществляется с помощью ключевого слова:
this.Для доступа к значению
thisиспользуется шаблон строки ($).Функция-расширение
.bold()принимает строку и возвращает ее в HTML-элементе<b>для выделения жирным шрифтом.
Проектирование на основе расширений
Функции-расширения можно объявлять где угодно, что позволяет создавать проекты на основе расширений. Такой подход отделяет основную функциональность от полезных, но необязательных возможностей, благодаря чему код становится понятнее и проще в сопровождении.
Хороший пример — класс HttpClient из библиотеки Ktor, который помогает выполнять сетевые запросы. Основу его функциональности составляет одна функция request(), принимающая всю информацию, необходимую для HTTP-запроса:
class HttpClient {
fun request(method: String, url: String, headers: Map<String, String>): HttpResponse {
// Network code
}
}
На практике наиболее распространены HTTP-запросы GET и POST. Библиотеке имеет смысл предоставить короткие имена для этих распространенных случаев. Однако для этого не нужно писать новый сетевой код — достаточно вызвать запрос с нужными параметрами. Другими словами, их удобно объявить в виде отдельных функций-расширений .get() и .post():
fun HttpClient.get(url: String): HttpResponse = request("GET", url, emptyMap())
fun HttpClient.post(url: String): HttpResponse = request("POST", url, emptyMap())
Эти функции .get() и .post() расширяют класс HttpClient. Они могут напрямую использовать функцию request() класса HttpClient, поскольку вызываются для экземпляра класса HttpClient, выступающего в роли получателя. С помощью этих функций-расширений можно вызвать функцию request() с подходящим HTTP-методом, что упрощает код и делает его понятнее:
class HttpClient {
fun request(method: String, url: String, headers: Map<String, String>): HttpResponse {
println("Requesting $method to $url with headers: $headers")
return HttpResponse("Response from $url")
}
}
fun HttpClient.get(url: String): HttpResponse = request("GET", url, emptyMap())
fun main() {
val client = HttpClient()
// Making a GET request using request() directly
val getResponseWithMember = client.request("GET", "https://example.com", emptyMap())
// Making a GET request using the get() extension function
// The client instance is the receiver
val getResponseWithExtension = client.get("https://example.com")
}
Такой подход, основанный на расширениях, широко используется в стандартной библиотеке Kotlin и других библиотеках. Например, у класса String есть множество функций-расширений, которые помогают работать со строками.
Подробнее о функциях-расширениях см. в разделе Расширения.
Практика
Упражнение 1
Напишите функцию-расширение с именем isPositive, которая принимает целое число и проверяет, является ли оно положительным.
fun Int.// Write your code here
fun main() {
println(1.isPositive())
// true
}
Упражнение 2
Напишите функцию-расширение с именем toLowercaseString, которая принимает строку и возвращает ее в нижнем регистре.
- Подсказка
Используйте функцию
.lowercase()для типаString.
fun // Write your code here
fun main() {
println("Hello World!".toLowercaseString())
// hello world!
}
© 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-intermediate-extension-functions.html