Сделайте свой код минимальным
Одна из наших главных обязанностей как разработчика — свести код к минимуму и избежать повторения кода. Generics — это одна из функций, которая обеспечивает лучшую производительность, меньше кода, повторно используемый код и многое другое. Поэтому я считаю, что каждый разработчик должен иметь представление о дженериках.
Зачем нужны дженерики?
Как мы видим, класс SearchUtil
будет принимать в качестве параметра список целых чисел. Функция searchItem
примет целое число (которое нужно было найти) в качестве входных данных и вернет результат. Это кажется прекрасным. не так ли?. Тогда в чем проблема?
Предположим, теперь вам нужно найти элемент, представляющий собой список строк или объектов. Что вы будете делать? Есть два возможных решения этой проблемы.
- Создайте еще один класс
SearchUtil
и функциюsearchItem
, которая будет принимать строки или тип объекта и возвращать результат. - Используйте дженерики
Решение 1, очевидно, не является хорошей идеей. Потому что нам нужно написать много кода, и многие коды будут повторяться. В этом случае на помощь приходят дженерики.
Что такое дженерики?
Согласно официальной документации,
Обобщения — это классы, структуры, интерфейсы и методы, которые имеют заполнители (параметры типа) для одного или нескольких типов, которые они хранят или используют. Универсальный класс коллекции может использовать параметр типа в качестве заполнителя для типа хранимых в нем объектов; параметры типа отображаются как типы его полей и типы параметров его методов. Универсальный метод может использовать свой параметр типа как тип возвращаемого значения или как тип одного из своих формальных параметров.
В двух словах,
Generics — гибкая система, позволяющая работать с любыми типами данных. Это изменяет бремя типа с вас на компилятор.
Думаю, это самое простое объяснение.
Дженерики в действии
Теперь мы преобразуем приведенный выше пример в дженерики. Чтобы преобразовать класс SearchUtil
в Generics, нам нужно изменить его, как показано ниже.
class SearchUtil<T>(private val list: List<T>)
Здесь T
указывает, что в качестве аргумента можно использовать любой тип.
Также нам нужно изменить функцию searchItem
.
fun searchItem(element: T, foundItem: (element: T?) -> Unit)
Теперь мы можем использовать любой тип, который мы хотим.
val searchUtil = SearchUtil(list = listOfObjects) val searchUtil = SearchUtil(list = listOfNumber)
Приведенный выше код будет работать без каких-либо проблем. Давайте посмотрим на реальный пример.
Здесь мы создали класс данных Person
. Мы проводим операцию по поиску listOfPerson
. Теперь, если мы хотим выполнить операцию поиска в списке целых чисел, мы можем сделать это, не внося никаких изменений в SearchUtil
или searchItem
.
val listOfNumbers = listOf(25, 46, 35) val searchUtil = SearchUtil(list = listOfNumbers) searchUtil.searchItem(element = 25) { println("Search result : $it") }
Это потрясающе, не так ли?
Это все на сегодня. Надеюсь, вы узнали что-то новое. Если у вас есть предложения, поделитесь ими в комментариях. Пока мы не встретимся снова… Ура!
Want to Connect? If you want to, you can connect with me on Twitter or LinkedIn.