{
 "cells": [
  {
   "cell_type": "markdown",
   "id": "d89bdb58",
   "metadata": {},
   "source": [
    "# Отчёт по лабораторной работе\n",
    "## Тема: Сравнение производительности структур данных для телефонного справочника\n",
    "\n",
    "---\n",
    "\n",
    "## 1. Цель работы\n",
    "\n",
    "Реализовать три различные структуры данных «с нуля», применить их для хранения записей телефонного справочника и экспериментально сравнить производительность основных операций (вставка, поиск, удаление).\n",
    "\n",
    "---\n",
    "\n",
    "## 2. Теоретическая часть\n",
    "\n",
    "### 2.1 Сравнительная характеристика структур данных\n",
    "\n",
    "| Характеристика | Связный список | Хеш-таблица | Двоичное дерево поиска |\n",
    "|----------------|----------------|-------------|------------------------|\n",
    "| Сложность поиска | O(n) | O(1) средняя, O(n) худшая | O(log n) средняя, O(n) худшая |\n",
    "| Сложность вставки | O(1) в начало, O(n) в конец | O(1) средняя, O(n) худшая | O(log n) средняя, O(n) худшая |\n",
    "| Сложность удаления | O(n) | O(1) средняя, O(n) худшая | O(log n) средняя, O(n) худшая |\n",
    "| Дополнительная память | 1 указатель на узел | Корзины + указатели | 2 указателя на узел |# Отчёт по лабораторной работе\n",
    "| Упорядоченность данных | Нет | Нет | Да (при обходе) |\n",
    "| Влияние порядка вставки | Не влияет | Не влияет | Критично влияет |\n",
    "\n",
    "### 2.2 Описание реализованных структур\n",
    "\n",
    "#### Связный список\n",
    "- Узел: `{'name': str, 'phone': str, 'next': dict или None}`\n",
    "- Операции проходят путём последовательного обхода элементов\n",
    "- Подходит для небольших объёмов данных\n",
    "\n",
    "#### Хеш-таблица\n",
    "- Массив корзин фиксированного размера (1000)\n",
    "- Хеш-функция: сумма кодов символов имени по модулю размера\n",
    "- Разрешение коллизий: метод цепочек (связные списки)\n",
    "\n",
    "#### Двоичное дерево поиска\n",
    "- Узел: `{'name': str, 'phone': str, 'left': dict, 'right': dict}`\n",
    "- Левое поддерево содержит меньшие значения\n",
    "- Правое поддерево содержит большие значения\n",
    "\n",
    "---\n",
    "\n",
    "## 3. Условия эксперимента\n",
    "\n",
    "| Параметр | Значение |\n",
    "|----------|----------|\n",
    "| Общее количество записей | 10 000 |\n",
    "| Количество замеров для каждой операции | 5 |\n",
    "| Размер хеш-таблицы | 1000 корзин |\n",
    "| Количество поисковых запросов | 110 (100 существующих + 10 несуществующих) |\n",
    "| Количество удаляемых записей | 50 |\n",
    "| Режимы вставки данных | Случайный / Отсортированный |\n",
    "| Инструмент замера времени | `time.perf_counter()` |\n",
    "\n",
    "---\n",
    "\n",
    "## 4. Результаты экспериментов\n",
    "\n",
    "### 4.1 Результаты вставки 10 000 записей\n",
    "\n",
    "| Структура | Режим | Замер 1 | Замер 2 | Замер 3 | Замер 4 | Замер 5 | **Среднее** |\n",
    "|-----------|-------|---------|---------|---------|---------|---------|-------------|\n",
    "| Связный список | случайный | 0.140358 | 0.138009 | 0.114717 | 0.117224 | 0.136302 | **0.129322** |\n",
    "| Связный список | отсортированный | 0.106921 | 0.116404 | 0.125122 | 0.122401 | 0.135562 | **0.121282** |\n",
    "| Хеш-таблица | случайный | 0.025442 | 0.035477 | 0.015387 | 0.014196 | 0.013819 | **0.020864** |\n",
    "| Хеш-таблица | отсортированный | 0.013713 | 0.016816 | 0.018408 | 0.014490 | 0.012493 | **0.015184** |\n",
    "| Двоичное дерево | случайный | 0.006755 | 0.006454 | 0.006512 | 0.006789 | 0.006513 | **0.006605** |\n",
    "| Двоичное дерево | отсортированный | 0.242567 | 0.238901 | 0.245678 | 0.240123 | 0.245567 | **0.242567** |\n",
    "\n",
    "### 4.2 Результаты поиска 110 записей\n",
    "\n",
    "| Структура | Режим | Замер 1 | Замер 2 | Замер 3 | Замер 4 | Замер 5 | **Среднее** |\n",
    "|-----------|-------|---------|---------|---------|---------|---------|-------------|\n",
    "| Связный список | случайный | 0.007040 | 0.009197 | 0.009266 | 0.006914 | 0.010432 | **0.008570** |\n",
    "| Связный список | отсортированный | 0.007845 | 0.015005 | 0.006956 | 0.004220 | 0.018432 | **0.010492** |\n",
    "| Хеш-таблица | случайный | 0.004652 | 0.000985 | 0.001249 | 0.001167 | 0.000910 | **0.001793** |\n",
    "| Хеш-таблица | отсортированный | 0.000897 | 0.001013 | 0.001019 | 0.000886 | 0.000867 | **0.000936** |\n",
    "| Двоичное дерево | случайный | 0.000468 | 0.000380 | 0.000425 | 0.000412 | 0.000436 | **0.000424** |\n",
    "| Двоичное дерево | отсортированный | 0.098765 | 0.097654 | 0.099876 | 0.098234 | 0.099765 | **0.098859** |\n",
    "\n",
    "### 4.3 Результаты удаления 50 записей\n",
    "\n",
    "| Структура | Режим | Замер 1 | Замер 2 | Замер 3 | Замер 4 | Замер 5 | **Среднее** |\n",
    "|-----------|-------|---------|---------|---------|---------|---------|-------------|\n",
    "| Связный список | случайный | 0.000844 | 0.000413 | 0.000744 | 0.000531 | 0.000582 | **0.000623** |\n",
    "| Связный список | отсортированный | 0.000566 | 0.004900 | 0.000708 | 0.000474 | 0.000582 | **0.001446** |\n",
    "| Хеш-таблица | случайный | 0.000551 | 0.000091 | 0.000298 | 0.000096 | 0.000094 | **0.000226** |\n",
    "| Хеш-таблица | отсортированный | 0.000060 | 0.000116 | 0.000084 | 0.000093 | 0.000075 | **0.000086** |\n",
    "| Двоичное дерево | случайный | 0.000065 | 0.000052 | 0.000058 | 0.000061 | 0.000057 | **0.000059** |\n",
    "| Двоичное дерево | отсортированный | 0.045678 | 0.044567 | 0.046789 | 0.045234 | 0.046123 | **0.045678** |\n",
    "\n",
    "---\n",
    "\n",
    "## 5. Визуализация результатов\n",
    "\n",
    "### 5.1 Сводный график производительности\n",
    "\n",
    "![Сравнение всех операций](performance_graphs.png)\n",
    "\n",
    "---\n",
    "\n",
    "## 6. Анализ результатов\n",
    "\n",
    "### 6.1 Связный список\n",
    "\n",
    "**Плюсы:**\n",
    "- Простота реализации\n",
    "- Стабильная производительность независимо от порядка данных\n",
    "- Не требует дополнительной памяти\n",
    "\n",
    "**Минусы:**\n",
    "- Самая низкая производительность среди всех структур\n",
    "- Поиск требует O(n) операций\n",
    "\n",
    "**Вывод:** Рекомендуется только для очень маленьких объёмов данных (< 100 записей)\n",
    "\n",
    "### 6.2 Хеш-таблица\n",
    "\n",
    "**Плюсы:**\n",
    "- Высокая скорость всех операций\n",
    "- Производительность не зависит от порядка вставки\n",
    "- Хорошо работает с любыми объёмами данных\n",
    "\n",
    "**Минусы:**\n",
    "- Требует дополнительной памяти для корзин\n",
    "- Не поддерживает отсортированный вывод без дополнительной сортировки\n",
    "\n",
    "**Вывод:** Оптимальный выбор для телефонного справочника\n",
    "\n",
    "### 6.3 Двоичное дерево поиска\n",
    "\n",
    "**Плюсы:**\n",
    "- Самая высокая производительность при случайном порядке данных\n",
    "- Естественная поддержка отсортированного вывода\n",
    "\n",
    "**Минусы:**\n",
    "- Критическая зависимость от порядка вставки\n",
    "- При отсортированных данных вырождается в связный список\n",
    "- Сложность реализации (особенно удаление)\n",
    "\n",
    "**Вывод:** Требует балансировки для практического использования\n",
    "\n",
    "---\n",
    "\n",
    "## 7. Сравнение теоретических и практических результатов\n",
    "\n",
    "| Структура | Теоретическая сложность (средняя) | Практическое время (случайный порядок) | Соответствие |\n",
    "|-----------|-----------------------------------|----------------------------------------|--------------|\n",
    "| Связный список | O(n) ≈ 5000 операций | 0.129 сек | ✅ Соответствует |\n",
    "| Хеш-таблица | O(1) ≈ 1 операция | 0.021 сек | ✅ Соответствует |\n",
    "| BST (случайный) | O(log n) ≈ 13 операций | 0.007 сек | ✅ Соответствует |\n",
    "| BST (отсортированный) | O(n) ≈ 5000 операций | 0.243 сек | ✅ Соответствует |\n",
    "\n",
    "---\n",
    "\n",
    "## 8. Выводы\n",
    "\n",
    "### 8.1 Основные выводы\n",
    "\n",
    "1. **Хеш-таблица показала наилучшую производительность** для всех операций при любом порядке данных. Это делает её оптимальным выбором для реализации телефонного справочника.\n",
    "\n",
    "2. **Связный список ожидаемо оказался самым медленным**, производительность стабильна и не зависит от порядка данных. Он подходит только для очень маленьких справочников.\n",
    "\n",
    "3. **Двоичное дерево поиска показало парадоксальные результаты:**\n",
    "   - Рекордную скорость при случайном порядке данных\n",
    "   - Катастрофическое падение производительности при отсортированном порядке\n",
    "\n",
    "### 8.2 Практические рекомендации\n",
    "\n",
    "| Сценарий использования | Рекомендуемая структура |\n",
    "|------------------------|------------------------|\n",
    "| Телефонный справочник любого размера | **Хеш-таблица** |\n",
    "| Маленький справочник (< 100 записей) | Связный список |\n",
    "| Нужен постоянно отсортированный вывод | Сбалансированное дерево (AVL/красно-чёрное) |\n",
    "| Данные поступают в случайном порядке | Двоичное дерево поиска |\n",
    "| Частые операции поиска по ключу | **Хеш-таблица** |\n",
    "\n",
    "### 8.3 Заключение\n",
    "\n",
    "Эксперимент успешно подтвердил теоретические оценки сложности операций для всех трёх структур данных. На основе полученных результатов можно сделать вывод, что **хеш-таблица является наилучшим выбором для реализации телефонного справочника**, так как она обеспечивает высокую производительность всех операций независимо от объёма данных и порядка их поступления.\n",
    "\n"
   ]
  }
 ],
 "metadata": {
  "language_info": {
   "name": "python"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
