Ты уже шаришь за списки и словари. Но есть одна структура, которую многие проходят мимо ушей, а зря.
Встречай множество (set) — неупорядоченная помойка для уникальных элементов, где поиск работает со скоростью света.
1. Что это за зверь?
Множество — это как список, но с тремя жирными отличиями:
· Нет повторений — каждый элемент только в одном экземпляре
· Нет порядка — забудь про индексы [0], тут всё перемешано
· Мгновенный поиск — проверить in или удалить элемент — O(1), как в словаре
Выглядит просто:
```python
fruits = {"яблоко", "банан", "апельсин"}
empty_set = set() # а вот {} — это словарь, не путай!
```
2. Как создать и что туда можно пихать
В множество можно положить только неизменяемые типы: числа, строки, кортежи. Списки и словари — нельзя (они изменяемые, Python ругнётся).
```python
valid = {1, "hello", (2, 3)} # ✅ ок
invalid = {1, [2, 3]} # ❌ TypeError
```
Создать из списка — легко:
```python
nums = [1, 2, 2, 3, 3, 3]
unique_nums = set(nums) # {1, 2, 3}
```
3. Главные плюшки: добавление, удаление, проверка
```python
s = {1, 2, 3}
# Добавить
s.add(4) # {1,2,3,4}
# Удалить (если нет — ошибка)
s.remove(4) # {1,2,3}
# Безопасно удалить (если нет — просто игнор)
s.discard(99) # ничего не случится
# Вытащить и удалить случайный элемент
popped = s.pop() # вернёт, например, 1
# Очистить всё
s.clear()
```
Проверка вхождения — rocket science:
```python
unique = {10, 20, 30, 40, 50}
if 30 in unique: # O(1) — моментально!
print("Есть")
```
4. Математика на максималках
Множества — это жесть как удобно, когда нужно сравнить группы. Забудь про вложенные циклы.
Объединение (всё из А и В)
```python
a = {1, 2, 3}
b = {3, 4, 5}
print(a | b) # {1,2,3,4,5}
print(a.union(b)) # то же самое
```
Пересечение (только общее)
```python
print(a & b) # {3}
print(a.intersection(b))
```
Разность (из А выкинуть то, что есть в В)
```python
print(a - b) # {1,2}
print(a.difference(b))
```
Симметрическая разность (не общее)
```python
print(a ^ b) # {1,2,4,5}
```
5. Где это реально юзать? Топ-3 задачи
1️⃣ Удалить дубликаты из списка — в одну строку
```python
dirty = ["a", "b", "a", "c", "b", "d"]
clean = list(set(dirty)) # ['a','b','c','d'] (порядок не гарантирован)
```
2️⃣ Быстрая проверка — есть ли у пользователя права?
```python
admins = {"Анна", "Олег", "Саша"}
user = "Олег"
if user in admins: # O(1) против O(n) у списка
print("Добро пожаловать, админ!")
```
3️⃣ Найти уникальных посетителей за день
```python
visitors_day1 = {"user1", "user2", "user3"}
visitors_day2 = {"user2", "user3", "user4"}
# Кто был в оба дня
both_days = visitors_day1 & visitors_day2 # {'user2','user3'}
# Новые посетители во второй день
new = visitors_day2 - visitors_day1 # {'user4'}
```
6. Подводные камни (чтобы не обжечься)
❌ Нет индексов — нельзя написать my_set[0]. Если нужен порядок — используй список.
❌ Нельзя положить список — но можно положить кортеж. Хочешь хранить список? Преврати в кортеж: set([(1,2), (3,4)]).
❌ Множество изменяемое — если нужно неизменяемое, бери frozenset(). Но это уже для гиков.
❌ Порядок не гарантирован — даже если в Python 3.7+ он стабилен при итерации, не рассчитывай на него.
7. Сравнение: список vs множество vs словарь (таблица для запоминания)
Характеристика Список Множество Словарь
Упорядоченность Да Нет Да (с 3.7)
Индексы Да Нет Только ключи
Уникальность элементов Нет Да (элементы) Да (ключи)
Поиск in O(n) O(1) O(1)
Изменяемость Да Да Да
Что хранит любые типы неизменяемые ключ: значение
8. Лайфхак для ускорения кода в 100 раз
Если у тебя есть список и ты часто проверяешь if x in my_list — конвертируй его во множество один раз и проверяй уже в сете.
```python
# Долго (O(n) на каждую проверку)
my_list = [i for i in range(100000)]
if 99999 in my_list: # полсекунды
# Быстро (один раз O(n) на создание, потом O(1))
my_set = set(my_list)
if 99999 in my_set: # моментально
```
Финальный кейс: реальный пример
Ты пишешь телеграм-бота, который собирает уникальные теги от пользователей:
```python
all_tags = set()
# Приходит новое сообщение с тегами
new_tags = ["python", "set", "python", "dict"]
all_tags.update(new_tags) # добавились только уникальные
print(all_tags) # {'python', 'set', 'dict'}
```
Никаких проверок, никаких дублей. Красота.
---
Короче: множество — это твой бро, когда нужно:
· убрать дубликаты
· быстро проверить вхождение
· делать пересечения и объединения
Не юзаешь множества — проходишь мимо топлива.
---
Подписывайся, если нужен разбор:
· frozenset (замороженное множество)
· как использовать множества для поиска пересечений в логах
· set comprehension (генератор множеств в одну строку)
Ставь лайк, если теперь будешь использовать сеты в каждом втором проекте. 🤘