# Лабораторная работа №1: Сравнительный анализ структур данных ## 1. Цель работы Реализация и экспериментальное сравнение производительности трех структур данных: 1. **Связный список (LinkedList)** 2. **Хеш-таблица (HashTable)** 3. **Бинарное дерево поиска (BST)** Структуры реализованы в процедурной парадигме (без использования классов). Особое внимание уделяется влиянию порядка входных данных (отсортированные vs случайные) на скорость операций вставки, поиска и удаления. ## 2. Методика эксперимента * **Объем выборки:** $N = 10\,000$ записей (имя, телефон). * **Режимы входных данных:** * *Случайный (Shuffled)* — имена перемешаны. * *Отсортированный (Sorted)* — имена идут по алфавиту. * **Измеряемые метрики:** * Время полной вставки $N$ элементов. * Время 110 операций поиска (100 существующих + 10 несуществующих). * Время 50 операций удаления. * **Инструментарий:** Замеры выполнены через `time.perf_counter()`, анализ данных — через `pandas`, визуализация — через `matplotlib`. * **Повторяемость:** Каждый тест запущен 5 раз для усреднения погрешности. ## 3. Результаты ### 3.1. Сводная таблица (Средние значения, сек) | Структура | Режим | Вставка (N) | Поиск (110) | Удаление (50) | | :--- | :--- | :--- | :--- | :--- | | **HashTable** | Случайный | **0.011** | **0.0001** | **0.00006** | | **HashTable** | Отсортированный | 0.010 | 0.0001 | 0.00006 | | **BST** | Случайный | 0.049 | 0.0005 | 0.0003 | | **BST** | Отсортированный | **29.91** | 0.093 | 0.106 | | **LinkedList** | Случайный | 10.82 | 0.134 | 0.057 | | **LinkedList** | Отсортированный | 6.79 | 0.059 | 0.035 | ### 3.2. Визуализация ![График производительности](data/plot.png) *(На графике ось Y логарифмическая. Это необходимо, так как диапазон времен составляет от $10^{-4}$ до $30$ секунд).* ## 4. Анализ результатов ### 4.1. Двоичное дерево поиска (BST) Наблюдается критическая зависимость от порядка данных. * **Случайные данные:** Дерево сбалансировано, операции выполняются быстро ($\approx O(\log N)$). Время вставки — 0.05 сек. * **Отсортированные данные:** Произошла деградация до вырожденного дерева (по сути, связного списка). Каждая вставка проходит до самого глубокого уровня. Время вставки составило **~30 секунд**. * **Вывод:** Простое BST не подходит для гарантированно упорядоченных данных. Для реальных систем требуется балансировка (AVL, Red-Black Trees). ### 4.2. Хеш-таблица Показала **стабильную производительность** вне зависимости от режима данных. * Время вставки $\approx 0.01$ сек. * Время поиска $\approx 0.0001$ сек (в 1000 раз быстрее поиска в списке). * Это подтверждает теоретическую сложность $O(1)$ (в среднем). Хеш-функция равномерно распределила ключи, коллизий практически не было. ### 4.3. Связный список Демонстрирует самую низкую производительность среди структур для задач поиска. * Вставка в случайном порядке занимает больше времени (10.8 сек), чем в отсортированном (6.8 сек), так как при случайном вставке элементы в среднем распределяются по списку равномернее, а при отсортированной вставке мы всегда идем до конца (хвост списка), что оптимизируется кешем процессора лучше, чем хаотичные переходы. * Поиск занимает $\approx 0.1$ сек ($O(N)$), что значительно медленнее хеш-таблицы. ## 5. Итоговые выводы 1. **Для быстрого поиска и вставки (Телефонный справочник):** Идеально подходит **Хеш-таблица**. Она обеспечивает мгновенный доступ к данным ($O(1)$) и не чувствительна к порядку поступления информации. 2. **Для хранения данных в отсортированном виде:** Теоретически подходит **BST**, но только при условии, что данные поступают в случайном порядке. Если данные отсортированы заранее, производительность падает в 600 раз. В реальных проектах следует использовать самобалансирующиеся деревья. 3. **Связный список:** Неэффективен для задач типа "словарь" или "справочник" из-за линейной сложности поиска. Имеет смысл применять только там, где важна структура очереди или стека, либо в условиях жесткой экономии памяти.