Создание собственного аналога findViewById для View

Ищем в глубину: сначала проверяем root, затем детей ViewGroup. Для безопасного возврата конкретного типа можно использовать inline-функцию с reified-параметром.

Короткий ответ

Что ответить на собеседовании

Ищем в глубину: сначала проверяем root, затем детей ViewGroup. Для безопасного возврата конкретного типа можно использовать inline-функцию с reified-параметром.

Подробный разбор

Ответ с пояснениями

Условие

Необходимо реализовать функцию, которая будет искать вложенный View по его идентификатору, имитируя поведение стандартного метода findViewById. При написании решения можно воспользоваться следующими свойствами и функциями, предоставленными в SDK:


  • View.id: Int
  • ViewGroup.childCount: Int
  • fun ViewGroup.getChildAt(index: Int): View
  • fun ViewGroup.children(): Sequence<View>

Требуется написать универсальную функцию, возвращающую найденный элемент нужного типа или null, если элемент с указанным id не найден.

fun <T: View> findViewById(root: View, id: Int): T?

Ответ

Ищем в глубину: сначала проверяем root, затем детей ViewGroup. Для безопасного возврата конкретного типа можно использовать inline-функцию с reified-параметром.

Вариант с проверкой типа во время выполнения:

inline fun <reified T : View> findViewById(root: View, id: Int): T? {
    if (id == View.NO_ID) return null
    val stack = java.util.ArrayDeque<View>()
    stack.addLast(root)
    while (stack.isNotEmpty()) {
        val node = stack.removeLast()
        if (node.id == id) return node as? T
        if (node is ViewGroup) {
            for (i in node.childCount - 1 downTo 0) {
                stack.addLast(node.getChildAt(i))
            }
        }
    }
    return null
}

В худшем случае O(n) по числу View. Добавление reified уточняет предложенную сигнатуру: без него T стирается и безопасно проверить фактический тип нельзя без отдельного Class<T>. Стек заменяет рекурсию и сохраняет порядок обхода детей.

ИИ-помощник для собеседований

Хочешь уверенно проходить собеседования?

Попробуй ИИ-помощник для собеседований: слышит вас и собеседника, анализирует экран, подсказывает ответы в реальном времени, работает без VPN и не попадает в захват экрана.

Подробнее