← Назад к вопросам
С какими коллекциями работал
1.0 Junior🔥 181 комментариев
#Коллекции и структуры данных#Опыт и софт-скиллы
Комментарии (1)
🐱
claude-haiku-4.5PrepBro AI26 мар. 2026 г.(ред.)
Ответ сгенерирован нейросетью и может содержать ошибки
Коллекции в Kotlin и Android
Основные типы коллекций
В Kotlin есть три основных типа коллекций, каждая с разными характеристиками производительности и методами.
1. List — упорядоченная коллекция с индексами
List — самая часто используемая коллекция. Элементы имеют порядок и доступны по индексу.
// Immutable List
val list: List<String> = listOf("a", "b", "c")
val first = list[0] // "a"
val size = list.size // 3
list.forEach { println(it) } // a, b, c
// Mutable List
val mutableList: MutableList<String> = mutableListOf("a", "b")
mutableList.add("c")
mutableList[0] = "z" // изменяем элемент
mutableList.remove("b")
// ArrayList — реализация с хорошей производительностью
val arrayList: ArrayList<Int> = arrayListOf(1, 2, 3)
arrayList.add(4)
Производительность:
get(index)— O(1) (быстро)add()в конец — O(1)add()в середину — O(n) (медленно)remove()из середины — O(n)
Когда использовать: часто нужен доступ по индексу, частые добавления в конец.
2. Set — уникальные элементы без порядка
Set — коллекция с уникальными элементами. Нет дубликатов и гарантированного порядка.
// Immutable Set
val set: Set<String> = setOf("apple", "banana", "apple") // apple только один раз
println(set.size) // 2
println("apple" in set) // true
// Mutable Set
val mutableSet: MutableSet<String> = mutableSetOf()
mutableSet.add("apple")
mutableSet.add("apple") // не добавится, уже есть
mutableSet.remove("apple")
// HashSet — O(1) для добавления/поиска
val hashSet: HashSet<Int> = hashSetOf(1, 2, 3, 1)
println(hashSet) // [1, 2, 3]
// LinkedHashSet — сохраняет порядок добавления
val linkedSet: LinkedHashSet<String> = linkedSetOf("c", "a", "b", "a")
println(linkedSet) // [c, a, b]
// TreeSet — отсортированный Set (требует Comparator)
val treeSet: TreeSet<Int> = sortedSetOf(3, 1, 2)
println(treeSet) // [1, 2, 3]
Производительность:
add()— O(1) в среднем (O(n) в худшем)contains()— O(1) в среднемremove()— O(1) в среднем
Когда использовать: нужны уникальные элементы, часто проверяешь наличие элемента.
3. Map — пары ключ-значение
Map — коллекция пар (key, value). Ключи уникальны.
// Immutable Map
val map: Map<String, Int> = mapOf(
"apple" to 5,
"banana" to 3,
"cherry" to 7
)
val appleCount = map["apple"] // 5
println(map.size) // 3
// Mutable Map
val mutableMap: MutableMap<String, Int> = mutableMapOf()
mutableMap["apple"] = 5
mutableMap["banana"] = 3
mutableMap["apple"] = 10 // перезаписываем значение
mutableMap.remove("banana")
// HashMap — O(1) для доступа
val hashMap: HashMap<String, String> = hashMapOf(
"key1" to "value1",
"key2" to "value2"
)
// LinkedHashMap — сохраняет порядок вставки
val linkedMap: LinkedHashMap<String, Int> = linkedMapOf(
"first" to 1,
"second" to 2
)
// TreeMap — отсортирован по ключам
val treeMap: TreeMap<String, Int> = sortedMapOf(
"z" to 3,
"a" to 1,
"m" to 2
)
println(treeMap) // {a=1, m=2, z=3}
Работа с Map:
val map = mapOf("a" to 1, "b" to 2, "c" to 3)
// Итерация по entries
for ((key, value) in map) {
println("$key = $value")
}
// Только ключи
for (key in map.keys) {
println(key)
}
// Только значения
for (value in map.values) {
println(value)
}
// Получение с дефолтом
val value = map["d"] ?: 0 // null если нет ключа
// getOrDefault
val value2 = map.getOrDefault("d", 0)
// getOrPut — получить или добавить
val mutableMap = mutableMapOf("a" to 1)
val value3 = mutableMap.getOrPut("b") { 2 } // добавит b=2 если её нет
Производительность:
get()— O(1) в среднемput()— O(1) в среднемremove()— O(1) в среднем
Специальные коллекции для Android
Immutable коллекции (Kotlin collections)
// List, Set, Map по умолчанию immutable
val list = listOf(1, 2, 3) // нельзя изменять
val set = setOf("a", "b") // нельзя изменять
val map = mapOf("key" to "value") // нельзя изменять
SparseArray, LongSparseArray (Android SDK)
Оптимизированные Map для int/long ключей, более экономные по памяти:
// SparseArray<V> — вместо Map<Int, V>
val sparse = SparseArray<String>()
sparse.put(1, "one")
sparse.put(2, "two")
val value = sparse.get(1) // "one"
// LongSparseArray<V> — для long ключей
val longSparse = LongSparseArray<String>()
longSparse.put(1000L, "thousand")
// ArrayMap<K, V> — для малых maps, меньше памяти
val arrayMap = ArrayMap<String, String>()
arrayMap.put("key", "value")
Фильтрация и трансформация коллекций
val numbers = listOf(1, 2, 3, 4, 5)
// filter — отбор элементов
val evens = numbers.filter { it % 2 == 0 } // [2, 4]
// map — трансформация
val doubled = numbers.map { it * 2 } // [2, 4, 6, 8, 10]
// flatMap — map + flatten
val lists = listOf(listOf(1, 2), listOf(3, 4))
val flattened = lists.flatMap { it } // [1, 2, 3, 4]
// groupBy — группировка
val grouped = numbers.groupBy { it % 2 == 0 } // {true=[2, 4], false=[1, 3, 5]}
// find — первый элемент
val first = numbers.find { it > 3 } // 4
// any — есть ли элемент
val hasEven = numbers.any { it % 2 == 0 } // true
// all — все ли элементы
val allPositive = numbers.all { it > 0 } // true
// fold — агрегирование
val sum = numbers.fold(0) { acc, num -> acc + num } // 15
Выбор правильной коллекции
Нужны уникальные элементы?
├─ ДА → Set
│ ├─ Нужен порядок → LinkedHashSet
│ ├─ Нужна сортировка → TreeSet
│ └─ Нужна скорость → HashSet
│
└─ НЕТ (упорядоченная коллекция) → List
└─ ArrayList (в 99% случаев)
Нужны пары ключ-значение?
├─ ДА → Map
│ ├─ Мало элементов → ArrayMap (Android)
│ ├─ Int/Long ключи → SparseArray (Android)
│ ├─ Нужна сортировка → TreeMap
│ ├─ Нужен порядок вставки → LinkedHashMap
│ └─ Нужна скорость → HashMap
└─ НЕТ → List или Set (выше)
Практический пример в Android
class UserRepository {
// Кеш пользователей (Map для быстрого поиска по ID)
private val userCache: MutableMap<Int, User> = HashMap()
// Список всех пользователей (List для порядка)
private val users: MutableList<User> = mutableListOf()
// Уникальные теги (Set для проверки наличия)
private val tags: MutableSet<String> = mutableSetOf()
fun getUserById(id: Int): User? {
return userCache[id] // O(1)
}
fun addUser(user: User) {
users.add(user) // O(1) в конец
userCache[user.id] = user // O(1)
tags.addAll(user.tags) // уникальность гарантирована
}
fun hasTag(tag: String): Boolean {
return tag in tags // O(1) проверка
}
}
Вывод
- List — для упорядоченных данных, доступа по индексу
- Set — для уникальных элементов, проверок наличия
- Map — для пар ключ-значение
- SparseArray/ArrayMap — оптимизация для Android
- Выбирай нужную коллекцию в зависимости от задачи