forked from UNN/2026-rff_mp
Merge pull request '[1,2] struck-data-task1, maze_task2' (#313) from nikolaevda/2026-rff_mp:nikolaevda into develop
Reviewed-on: UNN/2026-rff_mp#313
This commit is contained in:
commit
78ec64cb91
19
nikolaevda/docs/data/experiment_results.csv
Normal file
19
nikolaevda/docs/data/experiment_results.csv
Normal file
|
|
@ -0,0 +1,19 @@
|
||||||
|
Структура;Режим;Операция;Замер1(с);Замер2(с);Замер3(с);Замер4(с);Замер5(с);Среднее(с)
|
||||||
|
linked_list;случайный;вставка;4.743085900001461;4.702243700005056;4.426778699998977;4.3052682999987155;4.301903599996876;4.495856040000217
|
||||||
|
linked_list;случайный;поиск;0.040070499999274034;0.03833870000380557;0.038309099996695295;0.038068900001235306;0.037999300002411474;0.03855730000068434
|
||||||
|
linked_list;случайный;удаление;0.03337140000076033;0.03520829999615671;0.03318629999557743;0.03670069999498082;0.03511889999936102;0.03471711999736726
|
||||||
|
hash_table;случайный;вставка;0.054787300003226846;0.038778399997681845;0.038185400000656955;0.03906660000211559;0.040834699997503776;0.042330480000237
|
||||||
|
hash_table;случайный;поиск;0.00048270000115735456;0.0003393000006326474;0.00034130000130971894;0.0003389000048628077;0.0003389000048628077;0.00036822000256506724
|
||||||
|
hash_table;случайный;удаление;0.00018000000272877514;0.0001720000000204891;0.0001720000000204891;0.0001764999979059212;0.0001747999995131977;0.00017506000003777444
|
||||||
|
bst;случайный;вставка;0.04329969999525929;0.04011429999809479;0.0377946999942651;0.03973660000337986;0.03843010000127833;0.03987507999845548
|
||||||
|
bst;случайный;поиск;0.0005353999949875288;0.0004243000003043562;0.00040499999886378646;0.00041709999641170725;0.00041870000131893903;0.00044009999837726357
|
||||||
|
bst;случайный;удаление;0.08770270000240998;0.08755029999883845;0.09487290000106441;0.08564219999971101;0.08784590000141179;0.08872280000068714
|
||||||
|
linked_list;отсортированный;вставка;5.82706280000275;5.942067100004351;6.058909300001687;5.410613899999589;5.423316100001102;5.732393840001896
|
||||||
|
linked_list;отсортированный;поиск;0.05126659999950789;0.04912999999942258;0.04894649999914691;0.048823999997694045;0.0484264999977313;0.04931871999870054
|
||||||
|
linked_list;отсортированный;удаление;0.03424879999511177;0.03367250000155764;0.03369569999631494;0.03390580000268528;0.034035600001516286;0.033911679999437186
|
||||||
|
hash_table;отсортированный;вставка;0.03484389999357518;0.03386820000014268;0.033041399998182897;0.03465739999955986;0.035284899997350294;0.03433915999776218
|
||||||
|
hash_table;отсортированный;поиск;0.0005273999995552003;0.00044519999937620014;0.00037960000190651044;0.000374099996406585;0.0003724999987753108;0.00041975999920396134
|
||||||
|
hash_table;отсортированный;удаление;0.00017210000078193843;0.00017210000078193843;0.00017300000035902485;0.00017389999993611127;0.0001722999950288795;0.00017267999937757849
|
||||||
|
bst;отсортированный;вставка;17.43330440000136;17.245424400003685;17.230704699999478;17.4216249999954;17.25258659999963;17.31672901999991
|
||||||
|
bst;отсортированный;поиск;0.15691709999373415;0.15601930000411812;0.15765989999636076;0.15630209999653744;0.1590829000051599;0.15719625999918208
|
||||||
|
bst;отсортированный;удаление;0.08944690000498667;0.086433999997098;0.08745249999628868;0.08608390000154031;0.09040470000036294;0.08796440000005532
|
||||||
|
BIN
nikolaevda/docs/data/graphs.png
Normal file
BIN
nikolaevda/docs/data/graphs.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 72 KiB |
245
nikolaevda/docs/report_laba1.ipynb
Normal file
245
nikolaevda/docs/report_laba1.ipynb
Normal file
|
|
@ -0,0 +1,245 @@
|
||||||
|
{
|
||||||
|
"cells": [
|
||||||
|
{
|
||||||
|
"cell_type": "code",
|
||||||
|
"execution_count": null,
|
||||||
|
"id": "7cbca316",
|
||||||
|
"metadata": {},
|
||||||
|
"outputs": [],
|
||||||
|
"source": [
|
||||||
|
"{\n",
|
||||||
|
" \"cells\": [\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"start\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"# Отчёт по лабораторной работе\\n\",\n",
|
||||||
|
" \"## Тема: Сравнение производительности структур данных для телефонного справочника\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"goal\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 1. Цель работы\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Реализовать три различные структуры данных «с нуля», применить их для хранения записей телефонного справочника и экспериментально сравнить производительность основных операций (вставка, поиск, удаление).\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"conditions\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 2. Условия эксперимента\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Параметр | Значение |\\n\",\n",
|
||||||
|
" \"|----------|----------|\\n\",\n",
|
||||||
|
" \"| Общее число записей | 10 000 |\\n\",\n",
|
||||||
|
" \"| Каждый замер повторялся | 5 раз |\\n\",\n",
|
||||||
|
" \"| Количество существующих записей для поиска | 100 |\\n\",\n",
|
||||||
|
" \"| Количество несуществующих записей для поиска | 10 |\\n\",\n",
|
||||||
|
" \"| Количество элементов для удаления | 50 |\\n\",\n",
|
||||||
|
" \"| Размер хеш-таблицы | 2003 (простое число) |\\n\",\n",
|
||||||
|
" \"| Режимы тестирования | Случайный / Отсортированный |\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"graphs\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 3. Практические графики\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Информация о тестировании\\n\",\n",
|
||||||
|
" \"- Общее число записей: 10 000\\n\",\n",
|
||||||
|
" \"- Каждый замер повторялся: 5 раз\\n\",\n",
|
||||||
|
" \"- Количество существующих записей для случайного поиска: 100\\n\",\n",
|
||||||
|
" \"- Количество несуществующих записей для поиска: 10\\n\",\n",
|
||||||
|
" \"- Количество элементов для удаления: 50\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Рис. 1 – Тестирование вставки (логарифмическая шкала)**\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"analysis_bst\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 4. Анализ результатов\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Как порядок входных данных влияет на скорость вставки в BST (деградация до O(n) на отсортированных данных)?\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"По определению, при вставке отсортированных данных, структура бинарного дерева поиска вырождается в связный список.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Результаты тестирования:**\\n\",\n",
|
||||||
|
" \"- На случайных данных: время вставки ~0.037 секунд\\n\",\n",
|
||||||
|
" \"- На отсортированных данных: время вставки ~18.34 секунд (деградация в ~470 раз!)\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Заметим, что при случайных данных скорость вставки в бинарное дерево почти лишь немного уступает по скорости хеш-таблице. При отсортированных данных дерево фактически превращается в связный список, и из-за рекурсивной реализации вставки бинарное дерево становится даже медленнее связного списка.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"analysis_hash\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"### Почему хеш-таблица почти не чувствительна к порядку?\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Хеш-таблица не чувствительна к порядку данных, так как:\\n\",\n",
|
||||||
|
" \"1. Использует для распределения элементов хеш-значения данных (сложность операции одинакова для любых однотипных данных)\\n\",\n",
|
||||||
|
" \"2. Хеш-функция равномерно распределяет ключи по корзинам независимо от их порядка\\n\",\n",
|
||||||
|
" \"3. Вставка в конкретную корзину не зависит от соседних элементов\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Экспериментальное подтверждение:**\\n\",\n",
|
||||||
|
" \"- Случайный порядок: вставка = 0.0369 сек, поиск = 0.000355 сек\\n\",\n",
|
||||||
|
" \"- Отсортированный порядок: вставка = 0.0356 сек, поиск = 0.000380 сек\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Разница незначительна и находится в пределах погрешности измерений.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"analysis_list\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"### Почему связный список всегда медленен при поиске?\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Операция поиска в связном списке имеет линейную сложность **O(n)** независимо от порядка данных, так как:\\n\",\n",
|
||||||
|
" \"- Нет индексов для прямого доступа\\n\",\n",
|
||||||
|
" \"- Нет сортировки, позволяющей применять бинарный поиск\\n\",\n",
|
||||||
|
" \"- Приходится последовательно перебирать все элементы до найденного\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Структура | Сложность поиска | Время поиска (случайный) |\\n\",\n",
|
||||||
|
" \"|-----------|-----------------|--------------------------|\\n\",\n",
|
||||||
|
" \"| Связный список | O(n) | 0.0427 сек |\\n\",\n",
|
||||||
|
" \"| Хеш-таблица | O(1) средняя | 0.000355 сек |\\n\",\n",
|
||||||
|
" \"| BST (случайный) | O(log n) | 0.000527 сек |\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"analysis_delete\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"### Как удаление работает в каждой структуре?\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"#### Связный список\\n\",\n",
|
||||||
|
" \"Находим элемент перед удаляемым элементом и заменяем его поле `next` на `next.next`:\\n\",\n",
|
||||||
|
" \"```python\\n\",\n",
|
||||||
|
" \"current = head\\n\",\n",
|
||||||
|
" \"while current['next'] is not None:\\n\",\n",
|
||||||
|
" \" if current['next']['name'] == name:\\n\",\n",
|
||||||
|
" \" current['next'] = current['next']['next']\\n\",\n",
|
||||||
|
" \" return head\\n\",\n",
|
||||||
|
" \" current = current['next']\\n\",\n",
|
||||||
|
" \"```\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"#### Двоичное дерево поиска\\n\",\n",
|
||||||
|
" \"После того, как мы нашли узел, который необходимо удалить, возможны три случая:\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Случай 1:** У удаляемого узла нет детей → просто удаляем узел.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Случай 2:** У удаляемого узла есть только один ребёнок → ребёнок занимает место удалённого узла.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Случай 3:** У удаляемого узла есть оба ребёнка → находим минимальный элемент в правом поддереве (самый левый узел) и заменяем им удаляемый узел.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"#### Хеш-таблица\\n\",\n",
|
||||||
|
" \"1. Вычисляем хеш-индекс: `index = hash_func(name, len(buckets))`\\n\",\n",
|
||||||
|
" \"2. Находим нужную корзину: `buckets[index]`\\n\",\n",
|
||||||
|
" \"3. Удаляем элемент из связного списка в этой корзине\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Сравнение времени удаления:**\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Структура | Время удаления (случайный) | Сложность |\\n\",\n",
|
||||||
|
" \"|-----------|---------------------------|-----------|\\n\",\n",
|
||||||
|
" \"| Связный список | 0.0341 сек | O(n) |\\n\",\n",
|
||||||
|
" \"| Хеш-таблица | 0.00018 сек | O(1) средняя |\\n\",\n",
|
||||||
|
" \"| BST | 0.0793 сек | O(log n) средняя |\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"id\": \"conclusion\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 5. Вывод\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Мы реализовали и протестировали три различные структуры хранения данных: связный список, хеш-таблицу и двоичное дерево поиска. Сравнили скорость операций вставки, удаления и поиска для каждой структуры.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Итоговая таблица производительности (случайный порядок):\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Структура | Вставка (сек) | Поиск (сек) | Удаление (сек) |\\n\",\n",
|
||||||
|
" \"|-----------|---------------|-------------|----------------|\\n\",\n",
|
||||||
|
" \"| Связный список | 4.6031 | 0.0427 | 0.0341 |\\n\",\n",
|
||||||
|
" \"| Хеш-таблица | **0.0369** | **0.00036** | **0.00018** |\\n\",\n",
|
||||||
|
" \"| BST | 0.0369 | 0.00053 | 0.0793 |\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Рекомендации по выбору структуры данных:\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"1. **Хеш-таблица** – лучший выбор для телефонного справочника:\\n\",\n",
|
||||||
|
" \" - Не важен порядок хранения и извлечения данных\\n\",\n",
|
||||||
|
" \" - Требуется максимальная скорость поиска и вставки\\n\",\n",
|
||||||
|
" \" - Результат: **победитель по всем параметрам**\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"2. **Двоичное дерево поиска** – выбираем, если:\\n\",\n",
|
||||||
|
" \" - Нужно хранить данные с возможностью быстрого отсортированного обхода\\n\",\n",
|
||||||
|
" \" - Данные поступают в случайном порядке (иначе будет деградация)\\n\",\n",
|
||||||
|
" \" - Можно использовать сбалансированную версию (AVL, красно-чёрное)\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"3. **Связный список** – выбираем, если:\\n\",\n",
|
||||||
|
" \" - Нужно хранить данные в порядке поступления (очередь, стек)\\n\",\n",
|
||||||
|
" \" - Объём данных очень маленький (< 100 записей)\\n\",\n",
|
||||||
|
" \" - Простота реализации важнее производительности\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"---\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Заключение:** Для реализации телефонного справочника оптимальнее всего использовать **хеш-таблицу**, так как она обеспечивает наилучшую производительность для всех операций и не чувствительна к порядку входных данных.\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" }\n",
|
||||||
|
" ],\n",
|
||||||
|
" \"metadata\": {\n",
|
||||||
|
" \"kernelspec\": {\n",
|
||||||
|
" \"display_name\": \"Python 3\",\n",
|
||||||
|
" \"language\": \"python\",\n",
|
||||||
|
" \"name\": \"python3\"\n",
|
||||||
|
" },\n",
|
||||||
|
" \"language_info\": {\n",
|
||||||
|
" \"name\": \"python\",\n",
|
||||||
|
" \"version\": \"3.14.0\"\n",
|
||||||
|
" }\n",
|
||||||
|
" },\n",
|
||||||
|
" \"nbformat\": 4,\n",
|
||||||
|
" \"nbformat_minor\": 5\n",
|
||||||
|
"}"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"metadata": {
|
||||||
|
"language_info": {
|
||||||
|
"name": "python"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"nbformat": 4,
|
||||||
|
"nbformat_minor": 5
|
||||||
|
}
|
||||||
231
nikolaevda/docs/report_laba2.ipynb
Normal file
231
nikolaevda/docs/report_laba2.ipynb
Normal file
|
|
@ -0,0 +1,231 @@
|
||||||
|
{
|
||||||
|
"cells": [
|
||||||
|
{
|
||||||
|
"cell_type": "code",
|
||||||
|
"execution_count": null,
|
||||||
|
"id": "99cf9991",
|
||||||
|
"metadata": {},
|
||||||
|
"outputs": [],
|
||||||
|
"source": [
|
||||||
|
"{\n",
|
||||||
|
" \"cells\": [\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"# Лабораторная работа: Поиск выхода из лабиринта\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"## 1. Постановка задачи\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Разработать программу для загрузки лабиринта из текстового файла, поиска пути от стартовой клетки до выхода с возможностью выбора алгоритма поиска, визуализации процесса и экспериментального сравнения эффективности алгоритмов.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Основные требования\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"- Реализовать модель лабиринта (классы `Cell`, `Maze`)\\n\",\n",
|
||||||
|
" \"- Реализовать загрузку лабиринта из файла с символами `#` (стена), `S` (старт), `E` (выход)\\n\",\n",
|
||||||
|
" \"- Реализовать четыре алгоритма поиска пути: BFS, DFS, A*, Дейкстра\\n\",\n",
|
||||||
|
" \"- Реализовать класс-оркестратор `MazeSolver` с возможностью смены стратегии\\n\",\n",
|
||||||
|
" \"- Собрать статистику: время выполнения, количество посещённых клеток, длина пути\\n\",\n",
|
||||||
|
" \"- Провести эксперименты на лабиринтах разной сложности\\n\",\n",
|
||||||
|
" \"- Реализовать интерактивный режим с пошаговым управлением и отменой ходов\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Использованные паттерны проектирования GoF\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Паттерн | Где используется | Преимущества |\\n\",\n",
|
||||||
|
" \"|---------|-----------------|---------------|\\n\",\n",
|
||||||
|
" \"| **Builder** | `MazeBuilder`, `TextFileMazeBuilder` | Скрывает детали парсинга, легко добавлять новые форматы |\\n\",\n",
|
||||||
|
" \"| **Strategy** | `PathFindingStrategy`, BFS, DFS, A*, Дейкстра | Динамическая смена алгоритма |\\n\",\n",
|
||||||
|
" \"| **Observer** | `Observer`, `ConsoleDisplay` | Отделяет отображение от логики |\\n\",\n",
|
||||||
|
" \"| **Command** | `Command`, `MoveCommand`, `CommandInvoker` | Undo/Redo, история ходов |\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 2. Архитектура приложения\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Основные компоненты:\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"- **Модель** – `Cell`, `Maze` (хранение сетки, проверка стен, получение соседей)\\n\",\n",
|
||||||
|
" \"- **Загрузка** – `MazeBuilder`, `TextFileMazeBuilder` (парсинг `.txt`‑файлов)\\n\",\n",
|
||||||
|
" \"- **Алгоритмы** – `BFSStrategy`, `DFSStrategy`, `AStarStrategy`, `DijkstraStrategy`\\n\",\n",
|
||||||
|
" \"- **Оркестрация** – `MazeSolver` (управление стратегией, сбор статистики)\\n\",\n",
|
||||||
|
" \"- **Визуализация** – `ConsoleDisplay` (отрисовка лабиринта, игрока, пути)\\n\",\n",
|
||||||
|
" \"- **Интерактив** – `Player`, `MoveCommand`, `CommandInvoker` (перемещение, отмена/повтор)\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 3. Реализация алгоритмов поиска пути\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Алгоритм | Структура данных | Гарантия кратчайшего пути | Особенности |\\n\",\n",
|
||||||
|
" \"|----------|-----------------|---------------------------|-------------|\\n\",\n",
|
||||||
|
" \"| **BFS** | Очередь (`deque`) | Да | Обходит по слоям, гарантирует минимум шагов |\\n\",\n",
|
||||||
|
" \"| **DFS** | Стек | Нет | Углубляется до конца, экономичен по памяти |\\n\",\n",
|
||||||
|
" \"| **A*** | Приоритетная очередь (`heapq`) + эвристика | Да | Использует манхэттенское расстояние |\\n\",\n",
|
||||||
|
" \"| **Дейкстра** | Приоритетная очередь (`heapq`) | Да | Частный случай A* с эвристикой 0 |\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 4. Экспериментальная часть\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Тестовые лабиринты\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Имя | Размер | Описание |\\n\",\n",
|
||||||
|
" \"|-----|--------|----------|\\n\",\n",
|
||||||
|
" \"| tiny_simple | 10×10 | Маленький лабиринт с прямым путём |\\n\",\n",
|
||||||
|
" \"| small_empty | 20×20 | Пустой лабиринт без стен |\\n\",\n",
|
||||||
|
" \"| medium_dfs | 30×30 | Лабиринт среднего размера с тупиками |\\n\",\n",
|
||||||
|
" \"| medium_complex | 40×40 | Сложный запутанный лабиринт |\\n\",\n",
|
||||||
|
" \"| large_dfs | 50×50 | Большой лабиринт |\\n\",\n",
|
||||||
|
" \"| very_large_dfs | 100×100 | Очень большой лабиринт |\\n\",\n",
|
||||||
|
" \"| no_exit | 20×20 | Лабиринт без выхода |\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Каждый алгоритм запускался **5 раз** на каждом лабиринте, результаты усреднены.\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"### Результаты замеров\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Лабиринт | Алгоритм | Время (мс) | Посещено клеток | Длина пути |\\n\",\n",
|
||||||
|
" \"|----------|----------|------------|-----------------|------------|\\n\",\n",
|
||||||
|
" \"| tiny_simple (10x10) | BFS | 0.11 | 29 | 19 |\\n\",\n",
|
||||||
|
" \"| tiny_simple (10x10) | DFS | 0.07 | 29 | 19 |\\n\",\n",
|
||||||
|
" \"| tiny_simple (10x10) | A* | 0.17 | 29 | 19 |\\n\",\n",
|
||||||
|
" \"| tiny_simple (10x10) | Дейкстра | 0.15 | 29 | 19 |\\n\",\n",
|
||||||
|
" \"| small_empty (20x20) | BFS | 1.35 | 400 | 39 |\\n\",\n",
|
||||||
|
" \"| small_empty (20x20) | DFS | 1.02 | 400 | 191 |\\n\",\n",
|
||||||
|
" \"| small_empty (20x20) | A* | 2.61 | 400 | 39 |\\n\",\n",
|
||||||
|
" \"| small_empty (20x20) | Дейкстра | 1.02 | 400 | 39 |\\n\",\n",
|
||||||
|
" \"| medium_dfs (30x30) | BFS | 3.30 | 110 | 77 |\\n\",\n",
|
||||||
|
" \"| medium_dfs (30x30) | DFS | 2.58 | 80 | 77 |\\n\",\n",
|
||||||
|
" \"| medium_dfs (30x30) | A* | 0.51 | 88 | 77 |\\n\",\n",
|
||||||
|
" \"| medium_dfs (30x30) | Дейкстра | 0.55 | 110 | 77 |\\n\",\n",
|
||||||
|
" \"| no_exit (20x20) | BFS | 0.14 | 193 | 0 |\\n\",\n",
|
||||||
|
" \"| no_exit (20x20) | DFS | 0.07 | 52 | 0 |\\n\",\n",
|
||||||
|
" \"| no_exit (20x20) | A* | 0.16 | 162 | 0 |\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"### Графики\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"На графике представлено сравнение алгоритмов по трём метрикам: время выполнения, количество посещённых клеток и длина найденного пути.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Детальные графики по каждому лабиринту.\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 5. Анализ результатов\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Сравнение характеристик\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**BFS**\\n\",\n",
|
||||||
|
" \"- Гарантирует кратчайший путь (длина пути совпадает с A*)\\n\",\n",
|
||||||
|
" \"- Посещает много клеток (400 в пустом лабиринте)\\n\",\n",
|
||||||
|
" \"- Время работы стабильно, предсказуемо\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**DFS**\\n\",\n",
|
||||||
|
" \"- Самый быстрый на большинстве лабиринтов (0.07 мс на маленьком)\\n\",\n",
|
||||||
|
" \"- НЕ гарантирует кратчайший путь (в пустом лабиринте путь 191 вместо 39)\\n\",\n",
|
||||||
|
" \"- Посещает меньше клеток, чем BFS (80 против 110 на 30x30)\\n\",\n",
|
||||||
|
" \"- Отлично работает в лабиринтах без выхода (52 посещённые клетки)\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**A***\\n\",\n",
|
||||||
|
" \"- Всегда находит оптимальный путь (как BFS)\\n\",\n",
|
||||||
|
" \"- Посещает меньше клеток, чем BFS (88 против 110 на 30x30)\\n\",\n",
|
||||||
|
" \"- На 30x30 оказался самым быстрым (0.51 мс)\\n\",\n",
|
||||||
|
" \"- На пустом лабиринте медленнее из-за накладных расходов на эвристику\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"**Дейкстра**\\n\",\n",
|
||||||
|
" \"- На невзвешенных графах даёт те же результаты, что и BFS\\n\",\n",
|
||||||
|
" \"- Медленнее A* на сложных лабиринтах\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Ключевые выводы\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"1. **A* показывает лучший баланс** между скоростью и оптимальностью.\\n\",\n",
|
||||||
|
" \"2. **DFS – самый быстрый**, когда не важна длина пути.\\n\",\n",
|
||||||
|
" \"3. **BFS** остаётся простым и предсказуемым решением.\\n\",\n",
|
||||||
|
" \"4. **На пустых лабиринтах** DFS находит очень длинный путь.\\n\",\n",
|
||||||
|
" \"5. **В лабиринтах без выхода** DFS быстрее всех обнаруживает отсутствие пути.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Рекомендации по выбору алгоритма\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Сценарий | Рекомендуемый алгоритм | Обоснование |\\n\",\n",
|
||||||
|
" \"|----------|------------------------|-------------|\\n\",\n",
|
||||||
|
" \"| Нужен кратчайший путь + скорость | **A*** | Лучшие результаты на сложных лабиринтах |\\n\",\n",
|
||||||
|
" \"| Важна только скорость | **DFS** | Самый быстрый |\\n\",\n",
|
||||||
|
" \"| Простота реализации | **BFS** | Самый понятный алгоритм |\\n\",\n",
|
||||||
|
" \"| Проверка существования пути | **DFS** | Быстро находит или упирается в тупик |\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" },\n",
|
||||||
|
" {\n",
|
||||||
|
" \"cell_type\": \"markdown\",\n",
|
||||||
|
" \"metadata\": {},\n",
|
||||||
|
" \"source\": [\n",
|
||||||
|
" \"## 6. Заключение\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"В ходе лабораторной работы была разработана программа для поиска выхода из лабиринта с применением паттернов проектирования GoF.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"### Преимущества использованных паттернов\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"| Паттерн | Что было бы сложно изменить без него |\\n\",\n",
|
||||||
|
" \"|---------|--------------------------------------|\\n\",\n",
|
||||||
|
" \"| **Builder** | Добавление нового формата файлов потребовало бы переписывания всей логики загрузки |\\n\",\n",
|
||||||
|
" \"| **Strategy** | Смена алгоритма поиска потребовала бы изменения кода `MazeSolver` |\\n\",\n",
|
||||||
|
" \"| **Observer** | Добавление нового способа вывода потребовало бы изменения всех классов |\\n\",\n",
|
||||||
|
" \"| **Command** | Реализация отмены ходов привела бы к дублированию кода |\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Экспериментальное сравнение алгоритмов показало, что A* является оптимальным выбором для большинства сценариев. DFS остаётся лучшим выбором, когда скорость критичнее оптимальности пути.\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Программа предоставляет два режима работы:\\n\",\n",
|
||||||
|
" \"- **Интерактивный режим** – игра с ручным управлением, отменой и повторением ходов\\n\",\n",
|
||||||
|
" \"- **Экспериментальный режим** – автоматическое тестирование алгоритмов с сохранением результатов в CSV и построением графиков\\n\",\n",
|
||||||
|
" \"\\n\",\n",
|
||||||
|
" \"Разработанное решение демонстрирует преимущества объектно-ориентированного подхода и паттернов проектирования при создании гибких, расширяемых и легко поддерживаемых программ.\"\n",
|
||||||
|
" ]\n",
|
||||||
|
" }\n",
|
||||||
|
" ],\n",
|
||||||
|
" \"metadata\": {\n",
|
||||||
|
" \"kernelspec\": {\n",
|
||||||
|
" \"display_name\": \"Python 3\",\n",
|
||||||
|
" \"language\": \"python\",\n",
|
||||||
|
" \"name\": \"python3\"\n",
|
||||||
|
" },\n",
|
||||||
|
" \"language_info\": {\n",
|
||||||
|
" \"name\": \"python\",\n",
|
||||||
|
" \"version\": \"3.10.0\"\n",
|
||||||
|
" }\n",
|
||||||
|
" },\n",
|
||||||
|
" \"nbformat\": 4,\n",
|
||||||
|
" \"nbformat_minor\": 4\n",
|
||||||
|
"}"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"metadata": {
|
||||||
|
"language_info": {
|
||||||
|
"name": "python"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"nbformat": 4,
|
||||||
|
"nbformat_minor": 5
|
||||||
|
}
|
||||||
649
nikolaevda/task1/Zadanie1.py
Normal file
649
nikolaevda/task1/Zadanie1.py
Normal file
|
|
@ -0,0 +1,649 @@
|
||||||
|
import random
|
||||||
|
import time
|
||||||
|
import csv
|
||||||
|
import os
|
||||||
|
import traceback
|
||||||
|
import sys
|
||||||
|
|
||||||
|
sys.setrecursionlimit(30000)
|
||||||
|
|
||||||
|
def ll_insert(head, name, phone):
|
||||||
|
|
||||||
|
"""
|
||||||
|
проходит до конца (или сразу добавляет в конец)
|
||||||
|
возвращает новую голову (если вставка в начало) или изменяет список по ссылке.
|
||||||
|
"""
|
||||||
|
new_node = {'name': name, 'phone': phone, 'next': None}
|
||||||
|
|
||||||
|
# в случае пустого списка, новый узел становится головой
|
||||||
|
if head is None:
|
||||||
|
return new_node
|
||||||
|
|
||||||
|
# в противном случае проходим в конец списка
|
||||||
|
current = head
|
||||||
|
while current['next'] is not None:
|
||||||
|
if current['name'] == name:
|
||||||
|
current['phone'] = phone
|
||||||
|
return head
|
||||||
|
current = current['next']
|
||||||
|
|
||||||
|
# проверяем последний узел
|
||||||
|
if current['name'] == name:
|
||||||
|
current['phone'] = phone
|
||||||
|
else:
|
||||||
|
current['next'] = new_node
|
||||||
|
|
||||||
|
return head
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def ll_find(head, name):
|
||||||
|
|
||||||
|
"""
|
||||||
|
ищет узел по имени.
|
||||||
|
возвращает телефон или None
|
||||||
|
"""
|
||||||
|
current = head
|
||||||
|
|
||||||
|
while current is not None:
|
||||||
|
if current['name'] == name:
|
||||||
|
return current['phone']
|
||||||
|
current = current['next']
|
||||||
|
|
||||||
|
return None
|
||||||
|
|
||||||
|
|
||||||
|
def ll_delete(head, name):
|
||||||
|
|
||||||
|
"""
|
||||||
|
удаляет узел по имени.
|
||||||
|
возвращает новую голову.
|
||||||
|
"""
|
||||||
|
# если список пуст
|
||||||
|
if head is None:
|
||||||
|
return None
|
||||||
|
|
||||||
|
# если удаляем голову
|
||||||
|
if head['name'] == name:
|
||||||
|
new_head = head['next']
|
||||||
|
head['next'] = None
|
||||||
|
return new_head
|
||||||
|
|
||||||
|
# ищем узел для удаления
|
||||||
|
current = head
|
||||||
|
while current['next'] is not None:
|
||||||
|
if current['next']['name'] == name:
|
||||||
|
target = current['next']
|
||||||
|
current['next'] = target['next']
|
||||||
|
target['next'] = None # разрываем связь у удаляемого узла (иными словами, обнуление ссылки)
|
||||||
|
return head
|
||||||
|
current = current['next']
|
||||||
|
|
||||||
|
return head
|
||||||
|
|
||||||
|
def ll_collect(head, result_list):
|
||||||
|
"""собирает все данные из связного списка в result_list"""
|
||||||
|
current = head
|
||||||
|
while current is not None:
|
||||||
|
result_list.append((current['name'], current['phone']))
|
||||||
|
current = current['next']
|
||||||
|
|
||||||
|
|
||||||
|
def ll_list_all(head):
|
||||||
|
|
||||||
|
"""
|
||||||
|
собирает все записи в список и сортирует
|
||||||
|
"""
|
||||||
|
result = []
|
||||||
|
current = head
|
||||||
|
|
||||||
|
while current is not None:
|
||||||
|
result.append((current['name'], current['phone']))
|
||||||
|
current = current['next']
|
||||||
|
|
||||||
|
# ручная сортировка пузырьком
|
||||||
|
n = len(result)
|
||||||
|
for i in range(n):
|
||||||
|
for j in range(0, n - i - 1):
|
||||||
|
if result[j][0] > result[j + 1][0]:
|
||||||
|
result[j], result[j + 1] = result[j + 1], result[j]
|
||||||
|
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
def hash_table(size):
|
||||||
|
"""создание хеш-таблицы"""
|
||||||
|
return [None] * size
|
||||||
|
|
||||||
|
|
||||||
|
def hash_func(name, buckets_count):
|
||||||
|
"""
|
||||||
|
использует умножение на простое число для лучшего распределения
|
||||||
|
"""
|
||||||
|
h = 0
|
||||||
|
multiplier = 1
|
||||||
|
for char in name:
|
||||||
|
h = (h + ord(char) * multiplier) % buckets_count
|
||||||
|
multiplier = (multiplier * 31) % buckets_count
|
||||||
|
return h
|
||||||
|
|
||||||
|
|
||||||
|
def ht_insert(buckets, name, phone):
|
||||||
|
"""добавить или обновить запись"""
|
||||||
|
if buckets is None:
|
||||||
|
return
|
||||||
|
|
||||||
|
index = hash_func(name, len(buckets))
|
||||||
|
buckets[index] = ll_insert(buckets[index], name, phone)
|
||||||
|
|
||||||
|
|
||||||
|
def ht_find(buckets, name):
|
||||||
|
"""найти телефон по имени"""
|
||||||
|
idx = hash_func(name, len(buckets))
|
||||||
|
return ll_find(buckets[idx], name)
|
||||||
|
|
||||||
|
|
||||||
|
def ht_delete(buckets, name):
|
||||||
|
"""
|
||||||
|
удалить запись
|
||||||
|
"""
|
||||||
|
idx = hash_func(name, len(buckets))
|
||||||
|
buckets[idx] = ll_delete(buckets[idx], name)
|
||||||
|
|
||||||
|
|
||||||
|
def bubble_sort(records):
|
||||||
|
"""пузырьковая сортировка"""
|
||||||
|
n = len(records)
|
||||||
|
for i in range(n - 1):
|
||||||
|
swapped = False
|
||||||
|
for j in range(n - 1 - i):
|
||||||
|
if records[j][0] > records[j + 1][0]:
|
||||||
|
records[j], records[j + 1] = records[j + 1], records[j]
|
||||||
|
swapped = True
|
||||||
|
if not swapped:
|
||||||
|
break
|
||||||
|
return records
|
||||||
|
|
||||||
|
|
||||||
|
def ht_list_all(buckets):
|
||||||
|
"""
|
||||||
|
собрание всех записей и сортировка
|
||||||
|
"""
|
||||||
|
# Собираем все записи
|
||||||
|
full_data = []
|
||||||
|
for head in buckets:
|
||||||
|
ll_collect(head, full_data)
|
||||||
|
|
||||||
|
# Сортируем пузырьком
|
||||||
|
bubble_sort(full_data)
|
||||||
|
return full_data
|
||||||
|
|
||||||
|
#Hash_table1 = hash_table(3)
|
||||||
|
|
||||||
|
#ht_insert(Hash_table1, 'Alena', '010')
|
||||||
|
#ht_insert(Hash_table1, 'Helena', '111')
|
||||||
|
#ht_insert(Hash_table1, 'Gena', '222')
|
||||||
|
|
||||||
|
|
||||||
|
#print(ht_list_all(Hash_table1))
|
||||||
|
|
||||||
|
def bst_insert(root, name, phone):
|
||||||
|
"""
|
||||||
|
рекурсивная вставка или обновление записи
|
||||||
|
возвращает новый корень (если корень меняется)
|
||||||
|
"""
|
||||||
|
# если дерево пусто, создаём новый узел
|
||||||
|
if root is None:
|
||||||
|
return {'name': name, 'phone': phone, 'left': None, 'right': None}
|
||||||
|
|
||||||
|
# вставка в левое поддерево
|
||||||
|
if name < root['name']:
|
||||||
|
root['left'] = bst_insert(root['left'], name, phone)
|
||||||
|
|
||||||
|
# вставка в правое поддерево
|
||||||
|
elif name > root['name']:
|
||||||
|
root['right'] = bst_insert(root['right'], name, phone)
|
||||||
|
|
||||||
|
# имя уже существует — обновляем телефон
|
||||||
|
else:
|
||||||
|
root['phone'] = phone
|
||||||
|
|
||||||
|
return root
|
||||||
|
|
||||||
|
|
||||||
|
def bst_find(root, name):
|
||||||
|
"""
|
||||||
|
рекурсивный поиск телефона по имени
|
||||||
|
возвращает phone или None
|
||||||
|
"""
|
||||||
|
# не нашли
|
||||||
|
if root is None:
|
||||||
|
return None
|
||||||
|
|
||||||
|
# нашли
|
||||||
|
if root['name'] == name:
|
||||||
|
return root['phone']
|
||||||
|
|
||||||
|
# ищем в левом поддереве
|
||||||
|
elif name < root['name']:
|
||||||
|
return bst_find(root['left'], name)
|
||||||
|
|
||||||
|
# ищем в правом поддереве
|
||||||
|
else:
|
||||||
|
return bst_find(root['right'], name)
|
||||||
|
|
||||||
|
|
||||||
|
def bst_find_min(node):
|
||||||
|
"""вспомогательная функция: поиск узла с минимальным ключом"""
|
||||||
|
current = node
|
||||||
|
while current['left'] is not None:
|
||||||
|
current = current['left']
|
||||||
|
return current
|
||||||
|
|
||||||
|
|
||||||
|
def bst_delete(root, name):
|
||||||
|
"""
|
||||||
|
рекурсивное удаление записи по имени
|
||||||
|
возвращает новый корень
|
||||||
|
"""
|
||||||
|
# дерево пусто
|
||||||
|
if root is None:
|
||||||
|
return None
|
||||||
|
|
||||||
|
# спускаемся в левое поддерево
|
||||||
|
if name < root['name']:
|
||||||
|
root['left'] = bst_delete(root['left'], name)
|
||||||
|
|
||||||
|
# спускаемся в правое поддерево
|
||||||
|
elif name > root['name']:
|
||||||
|
root['right'] = bst_delete(root['right'], name)
|
||||||
|
|
||||||
|
# нашли удаляемый узел
|
||||||
|
else:
|
||||||
|
|
||||||
|
if root['left'] is None and root['right'] is None:
|
||||||
|
return None
|
||||||
|
|
||||||
|
|
||||||
|
elif root['left'] is None:
|
||||||
|
return root['right']
|
||||||
|
elif root['right'] is None:
|
||||||
|
return root['left']
|
||||||
|
|
||||||
|
|
||||||
|
# находим минимальный элемент в правом поддереве
|
||||||
|
successor = bst_find_min(root['right'])
|
||||||
|
|
||||||
|
# копируем данные из преемника в текущий узел
|
||||||
|
root['name'] = successor['name']
|
||||||
|
root['phone'] = successor['phone']
|
||||||
|
|
||||||
|
# удаляем преемника
|
||||||
|
root['right'] = bst_delete(root['right'], successor['name'])
|
||||||
|
|
||||||
|
return root
|
||||||
|
|
||||||
|
|
||||||
|
def bst_list_all(root, result=None):
|
||||||
|
"""
|
||||||
|
центрированный (in-order) обход дерева
|
||||||
|
рекурсивно собирает записи в отсортированном порядке
|
||||||
|
"""
|
||||||
|
if result is None:
|
||||||
|
result = []
|
||||||
|
|
||||||
|
if root is not None:
|
||||||
|
# сначала обходим левое поддерево (все меньшие ключи)
|
||||||
|
bst_list_all(root['left'], result)
|
||||||
|
|
||||||
|
# затем текущий узел
|
||||||
|
result.append((root['name'], root['phone']))
|
||||||
|
|
||||||
|
# затем правое поддерево (все большие ключи)
|
||||||
|
bst_list_all(root['right'], result)
|
||||||
|
|
||||||
|
return result
|
||||||
|
|
||||||
|
def generate_records(count=10000):
|
||||||
|
"""
|
||||||
|
генерация тестовых данных
|
||||||
|
70% уникальных имён, 30% повторяющихся (для коллизий)
|
||||||
|
"""
|
||||||
|
records = []
|
||||||
|
base_names = ["Алексей", "Борис", "Владимир", "Дмитрий", "Елена",
|
||||||
|
"Иван", "Мария", "Николай", "Ольга", "Павел"]
|
||||||
|
|
||||||
|
for i in range(count):
|
||||||
|
if random.random() < 0.7:
|
||||||
|
name = f"User_{i:05d}"
|
||||||
|
else:
|
||||||
|
name = random.choice(base_names) + f"_{random.randint(1, 100)}"
|
||||||
|
|
||||||
|
phone = f"+7-{random.randint(100,999)}-{random.randint(100,999)}-{random.randint(1000,9999)}"
|
||||||
|
records.append((name, phone))
|
||||||
|
|
||||||
|
shuffled = records.copy()
|
||||||
|
random.shuffle(shuffled)
|
||||||
|
sorted_records = sorted(records, key=lambda x: x[0])
|
||||||
|
|
||||||
|
return shuffled, sorted_records
|
||||||
|
|
||||||
|
|
||||||
|
def measure_insertion(structure_name, records):
|
||||||
|
"""
|
||||||
|
замер времени вставки
|
||||||
|
возвращает список замеров и заполненную структуру
|
||||||
|
"""
|
||||||
|
times = []
|
||||||
|
filled_structure = None
|
||||||
|
|
||||||
|
for run in range(5):
|
||||||
|
if structure_name == "linked_list":
|
||||||
|
structure = None
|
||||||
|
elif structure_name == "hash_table":
|
||||||
|
structure = hash_table(2003)
|
||||||
|
elif structure_name == "bst":
|
||||||
|
structure = None
|
||||||
|
|
||||||
|
start = time.perf_counter()
|
||||||
|
|
||||||
|
for name, phone in records:
|
||||||
|
if structure_name == "linked_list":
|
||||||
|
structure = ll_insert(structure, name, phone)
|
||||||
|
elif structure_name == "hash_table":
|
||||||
|
ht_insert(structure, name, phone)
|
||||||
|
elif structure_name == "bst":
|
||||||
|
structure = bst_insert(structure, name, phone)
|
||||||
|
|
||||||
|
end = time.perf_counter()
|
||||||
|
times.append(end - start)
|
||||||
|
|
||||||
|
if run == 4: # Сохраняем после последнего замера
|
||||||
|
filled_structure = structure
|
||||||
|
|
||||||
|
return times, filled_structure
|
||||||
|
|
||||||
|
|
||||||
|
def measure_search(structure_name, structure, search_names):
|
||||||
|
"""
|
||||||
|
замер времени поиска
|
||||||
|
возвращает список замеров
|
||||||
|
"""
|
||||||
|
times = []
|
||||||
|
|
||||||
|
for run in range(5):
|
||||||
|
start = time.perf_counter()
|
||||||
|
|
||||||
|
for name in search_names:
|
||||||
|
if structure_name == "linked_list":
|
||||||
|
ll_find(structure, name)
|
||||||
|
elif structure_name == "hash_table":
|
||||||
|
ht_find(structure, name)
|
||||||
|
elif structure_name == "bst":
|
||||||
|
bst_find(structure, name)
|
||||||
|
|
||||||
|
end = time.perf_counter()
|
||||||
|
times.append(end - start)
|
||||||
|
|
||||||
|
return times
|
||||||
|
|
||||||
|
|
||||||
|
def measure_deletion(structure_name, original_structure, delete_names):
|
||||||
|
"""
|
||||||
|
замер времени удаления
|
||||||
|
возвращает список замеров
|
||||||
|
"""
|
||||||
|
times = []
|
||||||
|
|
||||||
|
for run in range(5):
|
||||||
|
# создаём копию структуры
|
||||||
|
if structure_name == "linked_list":
|
||||||
|
all_records = ll_list_all(original_structure)
|
||||||
|
test_structure = None
|
||||||
|
for name, phone in all_records:
|
||||||
|
test_structure = ll_insert(test_structure, name, phone)
|
||||||
|
|
||||||
|
elif structure_name == "hash_table":
|
||||||
|
all_records = ht_list_all(original_structure)
|
||||||
|
test_structure = hash_table(2003)
|
||||||
|
for name, phone in all_records:
|
||||||
|
ht_insert(test_structure, name, phone)
|
||||||
|
|
||||||
|
elif structure_name == "bst":
|
||||||
|
all_records = bst_list_all(original_structure)
|
||||||
|
test_structure = None
|
||||||
|
for name, phone in all_records:
|
||||||
|
test_structure = bst_insert(test_structure, name, phone)
|
||||||
|
|
||||||
|
start = time.perf_counter()
|
||||||
|
|
||||||
|
for name in delete_names:
|
||||||
|
if structure_name == "linked_list":
|
||||||
|
test_structure = ll_delete(test_structure, name)
|
||||||
|
elif structure_name == "hash_table":
|
||||||
|
ht_delete(test_structure, name)
|
||||||
|
elif structure_name == "bst":
|
||||||
|
test_structure = bst_delete(test_structure, name)
|
||||||
|
|
||||||
|
end = time.perf_counter()
|
||||||
|
times.append(end - start)
|
||||||
|
|
||||||
|
return times
|
||||||
|
|
||||||
|
print(f"Текущая рабочая директория: {os.getcwd()}")
|
||||||
|
print(f"Путь к файлу: {os.path.abspath(__file__)}")
|
||||||
|
|
||||||
|
def run_experiment():
|
||||||
|
"""
|
||||||
|
запуск всех экспериментов и сохранение результатов
|
||||||
|
"""
|
||||||
|
|
||||||
|
current_dir = os.path.dirname(__file__)
|
||||||
|
docs_dir = os.path.dirname(current_dir)
|
||||||
|
csv_file = os.path.join(docs_dir, "experiment_results.csv")
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
os.makedirs(docs_dir, exist_ok=True)
|
||||||
|
|
||||||
|
print("ЭКСПЕРИМЕНТАЛЬНОЕ СРАВНЕНИЕ СТРУКТУР ДАННЫХ")
|
||||||
|
print("Телефонный справочник - 10000 записей")
|
||||||
|
print(f"\nРезультаты будут сохранены в: {csv_file}")
|
||||||
|
|
||||||
|
# генерация данных
|
||||||
|
print("\n1. Генерация тестовых данных...")
|
||||||
|
shuffled_records, sorted_records = generate_records(10000)
|
||||||
|
print(f"Сгенерировано 10000 записей")
|
||||||
|
print(f"Уникальных имён: {len(set([r[0] for r in shuffled_records]))}")
|
||||||
|
|
||||||
|
# подготовка имён для поиска и удаления
|
||||||
|
random.seed(42)
|
||||||
|
existing_names = [shuffled_records[i][0] for i in random.sample(range(10000), 100)]
|
||||||
|
nonexisting_names = [f"NotExist_{i}" for i in range(10)]
|
||||||
|
search_names = existing_names + nonexisting_names
|
||||||
|
delete_names = [shuffled_records[i][0] for i in random.sample(range(10000), 50)]
|
||||||
|
|
||||||
|
results = [["Структура", "Режим", "Операция",
|
||||||
|
"Замер1(с)", "Замер2(с)", "Замер3(с)", "Замер4(с)", "Замер5(с)",
|
||||||
|
"Среднее(с)"]]
|
||||||
|
|
||||||
|
# тестирование для каждого режима
|
||||||
|
for mode_name, records in [("случайный", shuffled_records),
|
||||||
|
("отсортированный", sorted_records)]:
|
||||||
|
|
||||||
|
print(f"\n2. Тестирование режима: {mode_name}")
|
||||||
|
|
||||||
|
|
||||||
|
for struct_name in ["linked_list", "hash_table", "bst"]:
|
||||||
|
print(f"\n {struct_name.upper()}:")
|
||||||
|
|
||||||
|
# вставка
|
||||||
|
print("Вставка 10000 записей...")
|
||||||
|
insert_times, filled_struct = measure_insertion(struct_name, records)
|
||||||
|
avg_insert = sum(insert_times) / 5
|
||||||
|
print(f"Время: {avg_insert:.4f} сек (среднее)")
|
||||||
|
|
||||||
|
# поиск
|
||||||
|
print("Поиск 110 записей (100 существующих + 10 которых нет)...")
|
||||||
|
search_times = measure_search(struct_name, filled_struct, search_names)
|
||||||
|
avg_search = sum(search_times) / 5
|
||||||
|
print(f"Время: {avg_search:.4f} сек (среднее)")
|
||||||
|
|
||||||
|
# удаление
|
||||||
|
print("Удаление 50 случайных записей...")
|
||||||
|
delete_times = measure_deletion(struct_name, filled_struct, delete_names)
|
||||||
|
avg_delete = sum(delete_times) / 5
|
||||||
|
print(f"Время: {avg_delete:.4f} сек (среднее)")
|
||||||
|
|
||||||
|
# сохраняем результаты
|
||||||
|
results.append([struct_name, mode_name, "вставка"] + insert_times + [avg_insert])
|
||||||
|
results.append([struct_name, mode_name, "поиск"] + search_times + [avg_search])
|
||||||
|
results.append([struct_name, mode_name, "удаление"] + delete_times + [avg_delete])
|
||||||
|
|
||||||
|
# сохранение CSV
|
||||||
|
print("\n3. Сохранение результатов...")
|
||||||
|
try:
|
||||||
|
with open(csv_file, "w", newline="", encoding="utf-8-sig") as f:
|
||||||
|
writer = csv.writer(f, delimiter=';')
|
||||||
|
writer.writerows(results)
|
||||||
|
print(f"Результаты сохранены в: {csv_file}")
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Ошибка сохранения: {e}")
|
||||||
|
|
||||||
|
# вывод табл.
|
||||||
|
print("СВОДНАЯ ТАБЛИЦА РЕЗУЛЬТАТОВ")
|
||||||
|
print(f"{'Структура':<15} {'Режим':<12} {'Операция':<10} {'Среднее время (сек)':<20}")
|
||||||
|
|
||||||
|
for row in results[1:]:
|
||||||
|
struct, mode, op, t1, t2, t3, t4, t5, avg = row
|
||||||
|
print(f"{struct:<15} {mode:<12} {op:<10} {avg:<20.6f}")
|
||||||
|
|
||||||
|
return results
|
||||||
|
|
||||||
|
def create_report_table(results):
|
||||||
|
"""Создание сводной таблицы"""
|
||||||
|
|
||||||
|
print("СВОДНАЯ ТАБЛИЦА (среднее время в секундах)")
|
||||||
|
|
||||||
|
print(f"{'Структура':<12} {'Режим':<12} {'Вставка':<12} {'Поиск':<12} {'Удаление':<12}")
|
||||||
|
|
||||||
|
summary = {}
|
||||||
|
for row in results[1:]:
|
||||||
|
struct, mode, op, _, _, _, _, _, avg = row
|
||||||
|
key = (struct, mode)
|
||||||
|
if key not in summary:
|
||||||
|
summary[key] = {}
|
||||||
|
summary[key][op] = avg
|
||||||
|
|
||||||
|
names = {'linked_list': 'LinkedList', 'hash_table': 'HashTable', 'bst': 'BST'}
|
||||||
|
for (struct, mode), ops in summary.items():
|
||||||
|
print(f"{names[struct]:<12} {mode:<12} {ops.get('вставка', 0):<12.6f} {ops.get('поиск', 0):<12.6f} {ops.get('удаление', 0):<12.6f}")
|
||||||
|
|
||||||
|
|
||||||
|
def print_analysis():
|
||||||
|
"""вывод краткого анализа"""
|
||||||
|
|
||||||
|
print("АНАЛИЗ РЕЗУЛЬТАТОВ")
|
||||||
|
|
||||||
|
print("""
|
||||||
|
1. Влияние порядка данных на BST:
|
||||||
|
- На случайных данных: быстро O(log n)
|
||||||
|
- На отсортированных: деградация до O(n) (дерево вырождается в список)
|
||||||
|
|
||||||
|
2. Хеш-таблица не чувствительна к порядку:
|
||||||
|
- Хеш-функция случайно распределяет данные по bucket'ам
|
||||||
|
- Порядок вставки не влияет на время операций
|
||||||
|
|
||||||
|
3. Связный список всегда медленен при поиске:
|
||||||
|
- Поиск требует последовательного прохода O(n)
|
||||||
|
- Нет индексов или сортировки для ускорения
|
||||||
|
|
||||||
|
4. Сравнение удаления:
|
||||||
|
- Связный список: O(n) — нужен поиск элемента
|
||||||
|
- Хеш-таблица: O(1) — прямой доступ по индексу
|
||||||
|
- BST: O(log n) в среднем, O(n) на отсортированных
|
||||||
|
|
||||||
|
5. Рекомендация для реальных задач:
|
||||||
|
- Хеш-таблица: частый поиск, словари, кэши
|
||||||
|
- BST (сбалансированный): нужны отсортированные данные
|
||||||
|
- Связный список: маленькие объёмы, очереди/стеки
|
||||||
|
- Для телефонного справочника ЛУЧШЕ: ХЕШ-ТАБЛИЦА
|
||||||
|
""")
|
||||||
|
|
||||||
|
def create_graphs(results):
|
||||||
|
"""Построение столбчатых диаграмм"""
|
||||||
|
import matplotlib.pyplot as plt
|
||||||
|
import numpy as np
|
||||||
|
|
||||||
|
data = {}
|
||||||
|
for row in results[1:]:
|
||||||
|
struct = row[0]
|
||||||
|
mode = row[1]
|
||||||
|
op = row[2]
|
||||||
|
avg = row[8]
|
||||||
|
|
||||||
|
if struct not in data:
|
||||||
|
data[struct] = {}
|
||||||
|
if mode not in data[struct]:
|
||||||
|
data[struct][mode] = {}
|
||||||
|
data[struct][mode][op] = avg
|
||||||
|
|
||||||
|
# Настройки
|
||||||
|
struct_names = {'linked_list': 'LinkedList', 'hash_table': 'HashTable', 'bst': 'BST'}
|
||||||
|
colors = {'linked_list': '#3498db', 'hash_table': '#2ecc71', 'bst': '#e74c3c'}
|
||||||
|
modes = ['случайный', 'отсортированный']
|
||||||
|
operations = ['вставка', 'поиск', 'удаление']
|
||||||
|
op_titles = ['Вставка (10000 записей)', 'Поиск (110 запросов)', 'Удаление (50 записей)']
|
||||||
|
|
||||||
|
fig, axes = plt.subplots(1, 3, figsize=(14, 5))
|
||||||
|
fig.suptitle('Сравнение производительности структур данных', fontsize=14, fontweight='bold')
|
||||||
|
|
||||||
|
for idx, (op, title) in enumerate(zip(operations, op_titles)):
|
||||||
|
ax = axes[idx]
|
||||||
|
x = np.arange(len(modes))
|
||||||
|
width = 0.25
|
||||||
|
multiplier = 0
|
||||||
|
|
||||||
|
for struct in ['linked_list', 'hash_table', 'bst']:
|
||||||
|
values = [data[struct][mode][op] for mode in modes]
|
||||||
|
bars = ax.bar(x + multiplier * width, values, width,
|
||||||
|
label=struct_names[struct], color=colors[struct])
|
||||||
|
|
||||||
|
for bar, val in zip(bars, values):
|
||||||
|
if val < 0.001:
|
||||||
|
ax.text(bar.get_x() + bar.get_width()/2, bar.get_height(),
|
||||||
|
f'{val:.6f}', ha='center', va='bottom', fontsize=7)
|
||||||
|
elif val < 0.01:
|
||||||
|
ax.text(bar.get_x() + bar.get_width()/2, bar.get_height(),
|
||||||
|
f'{val:.5f}', ha='center', va='bottom', fontsize=7)
|
||||||
|
else:
|
||||||
|
ax.text(bar.get_x() + bar.get_width()/2, bar.get_height(),
|
||||||
|
f'{val:.3f}', ha='center', va='bottom', fontsize=8)
|
||||||
|
multiplier += 1
|
||||||
|
|
||||||
|
ax.set_title(title)
|
||||||
|
ax.set_ylabel('Время (сек)')
|
||||||
|
ax.set_yscale('log')
|
||||||
|
ax.set_ylim(1e-5, 10)
|
||||||
|
ax.set_xticks(x + width)
|
||||||
|
ax.set_xticklabels(['Случайный', 'Отсортированный'])
|
||||||
|
ax.legend()
|
||||||
|
ax.grid(True, alpha=0.3, axis='y')
|
||||||
|
|
||||||
|
plt.tight_layout()
|
||||||
|
|
||||||
|
current_dir = os.path.dirname(__file__)
|
||||||
|
docs_dir = os.path.dirname(current_dir)
|
||||||
|
path = os.path.join(docs_dir, 'graphs.png')
|
||||||
|
plt.savefig(path, dpi=150)
|
||||||
|
plt.close()
|
||||||
|
print(f"\nГрафики сохранены: {path}")
|
||||||
|
return path
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
results = run_experiment()
|
||||||
|
create_report_table(results)
|
||||||
|
create_graphs(results)
|
||||||
|
print_analysis()
|
||||||
|
|
||||||
|
print("ЭКСПЕРИМЕНТ ВЫПОЛНЕН ПОЛНОСТЬЮ!")
|
||||||
1318
nikolaevda/task2/Zadanie2.py
Normal file
1318
nikolaevda/task2/Zadanie2.py
Normal file
File diff suppressed because it is too large
Load Diff
BIN
nikolaevda/task2/algorithm_comparison.png
Normal file
BIN
nikolaevda/task2/algorithm_comparison.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 297 KiB |
29
nikolaevda/task2/experiment_results.csv
Normal file
29
nikolaevda/task2/experiment_results.csv
Normal file
|
|
@ -0,0 +1,29 @@
|
||||||
|
maze_name;strategy;runs;avg_time_ms;min_time_ms;max_time_ms;avg_visited_cells;min_visited_cells;max_visited_cells;avg_path_length;min_path_length;max_path_length;path_found
|
||||||
|
tiny_simple (10x10);BFS (Поиск в ширину);5;0.10518000926822424;0.08800008799880743;0.16200006939470768;28.0;28;28;19.0;19;19;True
|
||||||
|
tiny_simple (10x10);DFS (Поиск в глубину);5;0.0728200189769268;0.061400001868605614;0.10630011092871428;28.0;28;28;19.0;19;19;True
|
||||||
|
tiny_simple (10x10);A Star;5;0.1740999985486269;0.1604999415576458;0.22060004994273186;28.0;28;28;19.0;19;19;True
|
||||||
|
tiny_simple (10x10);Дейкстра (Dijkstra);5;0.14854001346975565;0.14189991634339094;0.1716000260785222;28.0;28;28;19.0;19;19;True
|
||||||
|
small_empty (20x20);BFS (Поиск в ширину);5;1.350820017978549;1.2996000004932284;1.4386000111699104;400.0;400;400;39.0;39;39;True
|
||||||
|
small_empty (20x20);DFS (Поиск в глубину);5;1.0200999910011888;0.9803998982533813;1.131800003349781;400.0;400;400;191.0;191;191;True
|
||||||
|
small_empty (20x20);A Star;5;2.608919981867075;2.483000047504902;2.719299984164536;400.0;400;400;39.0;39;39;True
|
||||||
|
small_empty (20x20);Дейкстра (Dijkstra);5;2.270600013434887;2.1596000296995044;2.4237000616267323;400.0;400;400;39.0;39;39;True
|
||||||
|
medium_dfs (30x30);BFS (Поиск в ширину);5;0.3978000022470951;0.3643999807536602;0.5170999793335795;110.0;110;110;77.0;77;77;True
|
||||||
|
medium_dfs (30x30);DFS (Поиск в глубину);5;0.2578399842604995;0.25129993446171284;0.2742999931797385;80.0;80;80;77.0;77;77;True
|
||||||
|
medium_dfs (30x30);A Star;5;0.5116799846291542;0.47670002095401287;0.6345999427139759;88.0;88;88;77.0;77;77;True
|
||||||
|
medium_dfs (30x30);Дейкстра (Dijkstra);5;0.5545199848711491;0.5197999998927116;0.6467000348493457;110.0;110;110;77.0;77;77;True
|
||||||
|
medium_complex (40x40);BFS (Поиск в ширину);5;0.7289399858564138;0.7038000039756298;0.8005000418052077;199.0;199;199;137.0;137;137;True
|
||||||
|
medium_complex (40x40);DFS (Поиск в глубину);5;0.6589999888092279;0.46930008102208376;1.0472999420017004;141.0;141;141;137.0;137;137;True
|
||||||
|
medium_complex (40x40);A Star;5;0.9274400072172284;0.8467999286949635;1.2432000366970897;158.0;158;158;137.0;137;137;True
|
||||||
|
medium_complex (40x40);Дейкстра (Dijkstra);5;0.9650199906900525;0.9348000166937709;1.0183999547734857;199.0;199;199;137.0;137;137;True
|
||||||
|
large_dfs (50x50);BFS (Поиск в ширину);5;2.0312600303441286;1.7980000702664256;2.2323000011965632;459.0;459;459;277.0;277;277;True
|
||||||
|
large_dfs (50x50);DFS (Поиск в глубину);5;1.0593399871140718;1.0408000089228153;1.0833999840542674;287.0;287;287;277.0;277;277;True
|
||||||
|
large_dfs (50x50);A Star;5;2.5984000181779265;2.4158000014722347;2.81510001514107;427.0;427;427;277.0;277;277;True
|
||||||
|
large_dfs (50x50);Дейкстра (Dijkstra);5;2.5939000071957707;2.1897999104112387;3.5234999377280474;459.0;459;459;277.0;277;277;True
|
||||||
|
very_large_dfs (100x100);BFS (Поиск в ширину);5;35.92262000311166;34.23479991033673;40.153599926270545;4184.0;4184;4184;1897.0;1897;1897;True
|
||||||
|
very_large_dfs (100x100);DFS (Поиск в глубину);5;17.542819981463253;17.002100008539855;19.42270004656166;2216.0;2216;2216;1897.0;1897;1897;True
|
||||||
|
very_large_dfs (100x100);A Star;5;23.934299987740815;22.515099961310625;26.25090000219643;4017.0;4017;4017;1897.0;1897;1897;True
|
||||||
|
very_large_dfs (100x100);Дейкстра (Dijkstra);5;21.47540000732988;20.28030005749315;24.353899993002415;4184.0;4184;4184;1897.0;1897;1897;True
|
||||||
|
no_exit (20x20);BFS (Поиск в ширину);5;0.004719989374279976;0.001300009898841381;0.009899958968162537;0.0;0;0;0.0;0;0;False
|
||||||
|
no_exit (20x20);DFS (Поиск в глубину);5;0.0009800074622035027;0.000400003045797348;0.002900022082030773;0.0;0;0;0.0;0;0;False
|
||||||
|
no_exit (20x20);A Star;5;0.000700005330145359;0.000300002284348011;0.001800013706088066;0.0;0;0;0.0;0;0;False
|
||||||
|
no_exit (20x20);Дейкстра (Dijkstra);5;0.0009200070053339005;0.000400003045797348;0.002500019036233425;0.0;0;0;0.0;0;0;False
|
||||||
|
BIN
nikolaevda/task2/maze_detailed_analysis.png
Normal file
BIN
nikolaevda/task2/maze_detailed_analysis.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 409 KiB |
50
nikolaevda/task2/test_large_dfs_50x50.txt
Normal file
50
nikolaevda/task2/test_large_dfs_50x50.txt
Normal file
|
|
@ -0,0 +1,50 @@
|
||||||
|
##################################################
|
||||||
|
#S#.............................#.........#.#...##
|
||||||
|
#.###.#################.#.#####.#.#######.#.#.#.##
|
||||||
|
#...#...#...#.........#.#.....#...#.....#.#...#.##
|
||||||
|
###.#####.#.#.#######.#######.#######.###.#.###.##
|
||||||
|
#.#.......#.#.....#.#...#.....#.......#...#.#...##
|
||||||
|
#.#########.#####.#.###.#.#####.#####.#.###.#.####
|
||||||
|
#.........#...#...#...#.#.#.......#...#...#.#...##
|
||||||
|
#.#######.###.#.#####.#.#.#######.#.#####.#####.##
|
||||||
|
#.......#.#...#.....#...#.#.......#.....#.#.....##
|
||||||
|
#####.#.#.#.#######.#.###.#.#############.#.###.##
|
||||||
|
#...#.#.#.#...#...#.#.....#...#.....#...#.#.#...##
|
||||||
|
#.#.###.#.###.#.#.#.#######.#.#.###.#.#.#.#.#.####
|
||||||
|
#.#.#...#.#.#.#.#...#.....#.#.....#...#.#...#...##
|
||||||
|
#.#.#.###.#.#.#.###.#.###.#############.###.######
|
||||||
|
#.#...#.....#.#.#.#.#...#.#...........#.....#...##
|
||||||
|
#.###########.#.#.#.#.###.#.#########.#######.#.##
|
||||||
|
#.....#.......#.#...#.#...#.#.......#.....#...#.##
|
||||||
|
#.###.#.#######.#####.#.#.#.#####.#######.#.###.##
|
||||||
|
#.#.#...#.......#.....#.#.#.#...#.....#...#...#.##
|
||||||
|
#.#.#####.###.#.#.#####.###.#.#.#####.#.###.###.##
|
||||||
|
#.#.....#.#.#.#.#...#.#.....#.#.......#.#...#...##
|
||||||
|
#.#.###.#.#.#.#####.#.#######.#######.#.#.###.####
|
||||||
|
#.#.#.#.#.#.#.......#.........#.......#...#.#...##
|
||||||
|
#.#.#.#.#.#.###########.#.#######.#########.###.##
|
||||||
|
#.#...#.#...#...........#.#.....#...#...#...#...##
|
||||||
|
#.###.#.###.#########.#####.###.###.#.#.#.#.#.####
|
||||||
|
#...#.#.......#.....#.........#...#...#...#.#...##
|
||||||
|
###.#########.#.###.###.#########.###.#########.##
|
||||||
|
#.#.........#.#.#.#...#.#.........#...#.........##
|
||||||
|
#.#########.#.#.#.###.###.#.#######.###.#######.##
|
||||||
|
#...#.......#.#.#.....#...#.#...#...#...#.#...#.##
|
||||||
|
#.###.#######.#.#.#####.#####.#.#####.###.#.#.#.##
|
||||||
|
#...#.#.....#...#...#.....#...#.#.....#...#.#...##
|
||||||
|
###.#.###.#.#######.#####.#.###.#.#####.###.######
|
||||||
|
#...#...#.#.......#.#...#.#...#...#.......#.#...##
|
||||||
|
#.#.###.#.#######.#.#.#.#.###.###########.#.#.####
|
||||||
|
#.#.#.#...#.......#...#.....#.#...........#.#...##
|
||||||
|
#.#.#.#####.#############.###.#.#.#######.#.###.##
|
||||||
|
#.#.......#...#.....#...#.#...#.#.#...#...#...#.##
|
||||||
|
#.#######.###.###.#.#.#.###.###.#.###.#.#####.#.##
|
||||||
|
#.....#...#...#...#.#.#.....#...#...#...#.....#.##
|
||||||
|
#.###.#####.###.###.#.#######.#####.#####.#####.##
|
||||||
|
#.#...#.....#.....#.#.....#.#.....#.....#.#.....##
|
||||||
|
###.#.#.#####.###.#.###.#.#.#####.#####.#.#.###.##
|
||||||
|
#...#.#.#.....#...#...#.#.#...#...#...#.#...#.#.##
|
||||||
|
#.#####.#######.#####.###.#.###.###.#.#.#####.#.##
|
||||||
|
#...............#.........#.........#.#........E##
|
||||||
|
##################################################
|
||||||
|
##################################################
|
||||||
40
nikolaevda/task2/test_medium_complex_40x40.txt
Normal file
40
nikolaevda/task2/test_medium_complex_40x40.txt
Normal file
|
|
@ -0,0 +1,40 @@
|
||||||
|
########################################
|
||||||
|
#S..#...........#.....#...............##
|
||||||
|
###.#.#.#######.#####.#.#.##############
|
||||||
|
#.#.#.#.#.......#...#.#.#.......#.....##
|
||||||
|
#.#.#.#.#.#######.#.#.#.#######.#.###.##
|
||||||
|
#.#.#.#.#.#...#...#...#...#.....#...#.##
|
||||||
|
#.#.###.#.#.###.#.#######.#.#######.#.##
|
||||||
|
#.#.#...#.#.....#...#...#.#.#.....#.#.##
|
||||||
|
#.#.#.###.#########.#.#.#.#.#.###.#.#.##
|
||||||
|
#.#...#.#.....#.....#.#...#.#...#...#.##
|
||||||
|
#.#####.#####.#.###.#.#####.###.#####.##
|
||||||
|
#.......#.#...#.#...#...#.....#.#.#...##
|
||||||
|
#.#####.#.#.###.#######.#.#####.#.#.####
|
||||||
|
#.#.......#.#.#.......#.#.......#.#...##
|
||||||
|
#.#########.#.#.###.###.#########.###.##
|
||||||
|
#...#.......#.....#.#...#...........#.##
|
||||||
|
###.#.#######.#####.#.#######.#####.#.##
|
||||||
|
#...#.#...#...#...#.#.......#.....#.#.##
|
||||||
|
#.#.#.#.###.###.#.#.#######.#.###.#.#.##
|
||||||
|
#.#.#.#.....#...#.........#.#...#.#.#.##
|
||||||
|
#.###.#.#####.###########.#.#####.#.#.##
|
||||||
|
#.....#.#...#.#...........#.......#.#.##
|
||||||
|
#.#####.###.#.###################.###.##
|
||||||
|
#.....#.....#.#...........#.......#...##
|
||||||
|
#####.#######.#.#########.#.#######.####
|
||||||
|
#...#...#...#...#.......#.........#...##
|
||||||
|
#.#####.#.#.#####.#####.#########.###.##
|
||||||
|
#.....#...#.......#...#.......#.#...#.##
|
||||||
|
#.###.###############.#######.#.#.###.##
|
||||||
|
#.#...#...#...........#.....#.#...#...##
|
||||||
|
#.#.#.#.#.#####.#######.###.#.###.#.####
|
||||||
|
#.#.#...#.#.....#.......#...#...#.#...##
|
||||||
|
#.#.#####.#.###.#.#######.#.###.#.###.##
|
||||||
|
#.#...#.....#...#.#.....#.#...#.#...#.##
|
||||||
|
#.###.#########.#.#####.#.###.#.#.###.##
|
||||||
|
#...#.#...#...#.#.....#.#.#...#.#.#...##
|
||||||
|
###.#.#.#.#.#.#######.#.#.#####.###.#.##
|
||||||
|
#...#...#...#...........#...........#E##
|
||||||
|
########################################
|
||||||
|
########################################
|
||||||
30
nikolaevda/task2/test_medium_dfs_30x30.txt
Normal file
30
nikolaevda/task2/test_medium_dfs_30x30.txt
Normal file
|
|
@ -0,0 +1,30 @@
|
||||||
|
##############################
|
||||||
|
#S#.........#.......#.......##
|
||||||
|
#.#####.###.###.###.#.#####.##
|
||||||
|
#.#.....#.#...#.#.#.#.....#.##
|
||||||
|
#.#.#####.###.#.#.#.###.#.####
|
||||||
|
#...#.....#.#...#.#...#.#...##
|
||||||
|
#####.###.#.#####.###.#####.##
|
||||||
|
#.....#.#...#.......#...#...##
|
||||||
|
#.#####.###.#.#####.###.#.#.##
|
||||||
|
#.#.........#.....#...#.#.#.##
|
||||||
|
#.###.###############.#.#.####
|
||||||
|
#...#.#...............#.#...##
|
||||||
|
###.#.#####.#########.#.###.##
|
||||||
|
#...#.....#...#...#...#.....##
|
||||||
|
#.#######.###.#.###.#######.##
|
||||||
|
#.#.........#.#.....#.....#.##
|
||||||
|
#.#########.#.#.#########.#.##
|
||||||
|
#.#.......#...#.....#.....#.##
|
||||||
|
#.#.#####.#########.#.#####.##
|
||||||
|
#...#...#.#.......#...#.....##
|
||||||
|
#.###.#.#.#####.#####.#.######
|
||||||
|
#.#...#.#.....#.......#.....##
|
||||||
|
#.#.###.#####.###.#########.##
|
||||||
|
#.#.#.#.....#...#.#.......#.##
|
||||||
|
#.#.#.###.#####.#.#.#####.#.##
|
||||||
|
#...#.....#.....#.#...#.#.#.##
|
||||||
|
#####.#####.#########.#.#.#.##
|
||||||
|
#.........#.............#..E##
|
||||||
|
##############################
|
||||||
|
##############################
|
||||||
20
nikolaevda/task2/test_no_exit_20x20.txt
Normal file
20
nikolaevda/task2/test_no_exit_20x20.txt
Normal file
|
|
@ -0,0 +1,20 @@
|
||||||
|
####################
|
||||||
|
#S......#.........##
|
||||||
|
#######.#.###.######
|
||||||
|
#.....#.#...#.....##
|
||||||
|
#.#.#.#.#########.##
|
||||||
|
#.#.#.#.....#.....##
|
||||||
|
#.#.#######.#.###.##
|
||||||
|
#.#.......#.#...#.##
|
||||||
|
#.#####.###.###.#.##
|
||||||
|
#.#...#...#.....#.##
|
||||||
|
#.#.#.###.#######.##
|
||||||
|
#...#...#.........##
|
||||||
|
#######.############
|
||||||
|
#.....#.#.........##
|
||||||
|
#.###.#.#.#######.##
|
||||||
|
#.#...#.#.#.....#.##
|
||||||
|
#.#####.###.###.#.##
|
||||||
|
#...........#....###
|
||||||
|
####################
|
||||||
|
####################
|
||||||
20
nikolaevda/task2/test_small_empty_20x20.txt
Normal file
20
nikolaevda/task2/test_small_empty_20x20.txt
Normal file
|
|
@ -0,0 +1,20 @@
|
||||||
|
S...................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
....................
|
||||||
|
...................E
|
||||||
10
nikolaevda/task2/test_tiny_simple_10x10.txt
Normal file
10
nikolaevda/task2/test_tiny_simple_10x10.txt
Normal file
|
|
@ -0,0 +1,10 @@
|
||||||
|
S.########
|
||||||
|
...#######
|
||||||
|
#...######
|
||||||
|
##...#####
|
||||||
|
###...####
|
||||||
|
####...###
|
||||||
|
#####...##
|
||||||
|
######...#
|
||||||
|
#######...
|
||||||
|
########.E
|
||||||
100
nikolaevda/task2/test_very_large_dfs_100x100.txt
Normal file
100
nikolaevda/task2/test_very_large_dfs_100x100.txt
Normal file
|
|
@ -0,0 +1,100 @@
|
||||||
|
####################################################################################################
|
||||||
|
#S....#.......#...#...............................#.......#.....#.......#.....#.....#.....#.#.....##
|
||||||
|
#####.#.#.#####.#.#.###########.#####.#########.###.#.###.###.#.#.#####.#.#.#.#.###.#.###.#.#.#.#.##
|
||||||
|
#.....#.#.#.....#.......#.....#...#...#.......#.#...#...#.#...#...#...#.#.#.#...#.#.#.#...#...#.#.##
|
||||||
|
#.#######.#.#############.###.#####.###.#####.#.#.#####.#.#.#######.#.#.###.#####.#.#.#.#######.####
|
||||||
|
#.#.....#.....#.#.........#...#.....#...#.#...#.#.....#.#...#.#.....#.#.....#.....#.#.#.#.....#...##
|
||||||
|
#.#.###.#####.#.#.#########.###.###.#.###.#.###.#####.#.#####.#.#.#############.###.#.#.###.#.###.##
|
||||||
|
#...#...#...#...#...#.....#.#.....#.#.....#.#.....#.#.#.....#...#.........#.....#...#.#.#...#.....##
|
||||||
|
#####.###.#.#######.#.#####.#####.#######.#.#####.#.#.#####.#############.#.#.###.###.#.#.#######.##
|
||||||
|
#...#.....#.......#.#.......#...#.......#.#...#.#...#.#...#...#...#...#...#.#.....#...#...#.....#.##
|
||||||
|
#.###############.#.#.#######.#.#.#####.#.###.#.#.###.###.###.#.#.#.#.#.###.#########.###.#.###.#.##
|
||||||
|
#...#...#.........#.#.#.......#.#.#...#...#...#.#.#...#.....#...#...#.#.....#.........#...#...#.#.##
|
||||||
|
#.#.#.#.#.#########.#.#.#######.#.###.#####.###.#.#.###.#########.###.#.#####.#.###########.###.#.##
|
||||||
|
#.#...#...#.........#.#.#.....#.#.#.....#...#.....#.#...#.......#.#...#.......#.#...........#...#.##
|
||||||
|
#.###############.###.#.#.###.#.#.#.###.#.#####.###.###.#.#####.#.#.#############.###########.######
|
||||||
|
#.#...............#.#.#.....#.#.#...#...#.....#.#.#.....#...#...#.#.....#.....#...#.......#.#.#...##
|
||||||
|
#.###.#############.#.#######.#.#######.#####.#.#.#####.###.#.#######.#.#.###.#.###.#####.#.#.#.#.##
|
||||||
|
#.....#...#.....#...#.........#.......#.#...#.#...#...#...#.#.#.....#.#.#...#.#...#.#.......#...#.##
|
||||||
|
#######.#.#.#.###.#.#################.#.#.#.#.###.###.#.###.#.###.#.#.#.#.###.###.#.#.###########.##
|
||||||
|
#.......#...#.#...#...#.....#.......#.#.#.#.#...#.....#.#...#.....#.#.#...#...#...#.#.#...#.....#.##
|
||||||
|
#.###########.#.###.#.#.###.#.#.#####.#.###.###.#######.#.#########.#.#####.#.#.###.#.#.#.#.###.#.##
|
||||||
|
#...#.#.......#...#.#.#.#.#.#.#...#...#.#.....#...#.....#.#.......#.#.....#.#.#.#...#.#.#.#.#...#.##
|
||||||
|
#.#.#.#.#########.#.#.#.#.#.#####.#.###.#.#.#####.#.#####.#.###.#.#.#####.#.#.#.#.###.#.###.#.###.##
|
||||||
|
#.#.#.......#...#.#.#...#...#...#.#...#...#.#...#.#.#.#...#...#.#.#.....#.#.#.#.#.#.....#...#.#...##
|
||||||
|
###.#######.###.#.#.#######.#.#.#.###.###.###.#.#.#.#.#.#####.#.#######.#.#.###.#.#.#####.###.#.####
|
||||||
|
#...#...#.......#.#.......#...#.....#.#...#...#.#.....#.....#.#...#...#.#.#.......#.#.....#.#.#...##
|
||||||
|
#.###.#.#########.#######.#######.###.#.###.###.#####.#####.#####.#.#.#.#.###########.#####.#.###.##
|
||||||
|
#.....#.........#.#.#.....#...#...#...#...#...#...#.....#...#...#...#...#...#.....#...#...#.#.....##
|
||||||
|
#.#############.#.#.#.#####.###.###.###.#####.###.#.#####.###.#.###.#########.###.#.###.#.#.#####.##
|
||||||
|
#.#...#.....#...#.#.#.#.........#.#.#...#.....#...#...#...#...#...#.......#...#.#...#...#...#...#.##
|
||||||
|
#.#.#.#.###.#.#.#.#.#.#####.#####.#.#####.#####.#######.###.#####.#######.#.###.#####.#.#####.#.#.##
|
||||||
|
#...#...#.#.#.#.#...#.#...#.......#...#...#.....#...#...#...#...#.#.....#...#.........#.#...#.#...##
|
||||||
|
#########.#.#.###.###.#.#.#####.#####.#.###.#####.#.#.#.#.###.#.#.#.#.#######.#########.#.#.#.######
|
||||||
|
#...#.......#.#...#...#.#.....#.#...#...#...#.....#.#.#.#...#.#...#.#.........#.#.....#.#.#.#.#...##
|
||||||
|
#.###.#######.#.###.###.#####.#.#.#.#####.###.#####.#.#####.#.#####.#######.###.#.#.###.#.#.#.#.####
|
||||||
|
#...#.#...#...#...#.....#...#.#.#.#.....#...#...#...#.#.....#.#...#.#.....#.#.....#.....#.#.#.#...##
|
||||||
|
###.#.###.#.#####.#########.#.###.#.#######.###.###.#.#.#####.###.#.#.###.#.#.#######.###.#.#.###.##
|
||||||
|
#...#...#.#.#.....#.........#.#...#.......#...#...#.#.....#...#...#...#...#.#...#...#.#...#.#.....##
|
||||||
|
#.#.###.#.#.#.#####.###.#####.#.#######.#####.###.#.#######.###.#######.###.#####.#.###.###.#####.##
|
||||||
|
#.#.#...#.#...#.......#.....#...#.....#.....#...#.#.........#.........#.#.#.......#...#.#.#.......##
|
||||||
|
#.###.###.#################.#####.#######.#.###.#.###########.###.#####.#.###########.#.#.##########
|
||||||
|
#...#.#.........#.......#.......#.#.....#.#...#.#.#.#.......#.#.#.....#.#.........#...#...#.......##
|
||||||
|
###.#.###.#####.#.#####.#.#####.#.#.###.#.###.#.#.#.#.#####.#.#.#####.#.#.#####.###.#.###.#.#####.##
|
||||||
|
#...#.#...#...#...#...#...#.......#.#.#.#.#...#.#.#...#...#.#.#.....#.#...#.....#...#.#.#.#...#...##
|
||||||
|
#.#.#.#.###.#######.#######.#######.#.#.###.###.#.#.###.#.#.#.###.###.###.#######.###.#.#.#####.#.##
|
||||||
|
#.#.#.#.#.#...#.....#...#...#...#...#.......#...#.#...#.#...#...#...#.....#.......#.#...#.#.....#.##
|
||||||
|
#.###.#.#.#.#.#.###.#.#.#.###.#.#.#######.###.###.###.#.#######.###.#######.#######.###.#.#.#####.##
|
||||||
|
#.#...#.#.#.#.#...#...#...#.#.#.#...#...#.#...#...#...#.#.....#...#...#.....#.........#.#...#.....##
|
||||||
|
#.#.###.#.#.#.###.#########.#.#.###.#.#.###.###.###.###.#.#.#.###.#.#.#.#####.#.#######.#####.######
|
||||||
|
#...#...#...#...#.#.........#.#.....#.#.....#...#...#...#.#.#.#...#.#.#...#...#.............#.#...##
|
||||||
|
#.###.###.###.###.#####.###.#.#.#####.#########.#.###.###.#.#.#.###.#.###.#.#################.#.####
|
||||||
|
#.....#.#.#.#...#.....#...#.#.#.#.....#.........#.#.#.....#.#.#.#...#...#.#.............#.....#...##
|
||||||
|
#######.#.#.###.#####.#.###.#.###.#######.#######.#.#######.#.#.#.#.###.#.###############.#######.##
|
||||||
|
#.....#.......#...#...#.#...#.#...#.....#.#...#...#...#.....#.#.#.#...#.#.......#.......#.#.......##
|
||||||
|
#.#.###.#######.###.#####.#.#.#.#####.#.#.#.#.#.###.###.###.###.#.###.#########.#.#####.#.#.#####.##
|
||||||
|
#.#.#...#.#.....#...#.....#.#...#.....#.#.#.#...#.....#...#.#...#...#.........#...#...#...#...#...##
|
||||||
|
#.###.###.#.#.###.###.###########.#####.#.#.#######.#.###.#.#.###.###########.#####.#.#######.#.####
|
||||||
|
#.........#.#.#...#.........#.........#...#.......#.#...#.#.#...#.#...........#.....#.#.....#.#.#.##
|
||||||
|
#.#########.#.#.###.#######.#.#######.###########.#####.#.#####.###.#########.#.#####.#.###.#.#.#.##
|
||||||
|
#.#...#...#.#.#.#.........#...#.....#.#.....#...#.....#.#.......#...#.....#...#...#.#...#.#.#.#...##
|
||||||
|
#.###.#.#.#.#.#.#############.#.#.###.#.#.#.#.#.#####.#.#########.###.###.#.#####.#.#####.#.#.######
|
||||||
|
#.....#.#...#.#.............#...#.#...#.#.#.#.#.....#.#.............#.#...#.....#.#...#...#.#.....##
|
||||||
|
#######.#.#################.#####.#.###.#.###.#.#.###.#.#######.###.###.#.#####.#.#.#.#.#.#.#.###.##
|
||||||
|
#.......#.#...........#...#.#.....#.#...#.....#.#.#...#.#.....#...#...#.#.....#.#.#.#...#.#.#...#.##
|
||||||
|
#.#########.#####.###.#.###.#####.#.#.#########.#.#.#####.###.###.###.#.#######.#.#######.#.#####.##
|
||||||
|
#.....#.....#...#.#...#.#...#...#.#.#.........#.#.#.#.....#.#.#.#.#...#.......#...#.......#.#.....##
|
||||||
|
#.###.#.#####.#.#.###.#.#.###.#.###.#########.#.###.#.#####.#.#.#.#.###.#####.#####.#.#####.#.###.##
|
||||||
|
#.#...#...#...#.#...#...#.#...#.....#.....#...#...#.#.#.....#.#...#...#.#.....#.....#.#.....#.#...##
|
||||||
|
###.#.###.###.#####.#.###.#.#########.###.#.#####.#.#.###.#.#.###.###.###.###.#.###.###.#####.######
|
||||||
|
#...#...#...#.#.....#.#...#.#.....#.#.#.#.......#.#.#...#.#.#...#.#.#...#.#...#...#.#...#.........##
|
||||||
|
#.#.#######.#.#.#####.#.###.#.#.#.#.#.#.#########.#.###.#.#####.#.#.###.#.#.###.###.#.###########.##
|
||||||
|
#.#.#...#.....#...#...#.#...#.#.#...#...#.#.......#.....#.#.....#.....#.#.#.#...#...#...#.........##
|
||||||
|
#.###.#.#.#######.#####.#.#.#.#.###.###.#.#.###.#########.#.#########.#.#.###.###.#####.#.#######.##
|
||||||
|
#...#.#...#.....#.#.....#.#.#.#.#.#...#.#.#.#...#.........#...#.#.....#.#.....#.#.....#.#.#.....#.##
|
||||||
|
#.#.#.#####.###.#.#.#######.#.#.#.###.#.#.#.#####.#######.###.#.#.#####.#.#####.#####.#.#.#.#.###.##
|
||||||
|
#.#.#.#.#...#.#...#.........#.#.#.....#...#...#...#.....#...#.#...#.....#.......#...#.#.#.#.#.....##
|
||||||
|
#.#.#.#.#.###.###.#############.#########.###.#.###.###.#.###.#.###.###########.#.#.#.#.#.###.######
|
||||||
|
#.#.#...#...#.......#...........#.......#...#.#...#...#.#.#...#.#...#.........#...#.#.#.#...#.....##
|
||||||
|
###.###.###.#########.###.#######.###.#.###.#.###.#####.#.#.#####.###.#.#####.###.###.#.###.#####.##
|
||||||
|
#...#.#...#.......#...#.#.......#.#.#.#...#.#...#.....#.#.#...#...#...#...#.....#.#...#...#.#...#.##
|
||||||
|
#.#.#.###.#######.#.###.#######.#.#.#.#####.###.#####.#.#.###.#.###.#####.#######.#.#####.#.#.#.####
|
||||||
|
#.#.#.#.........#.#.#...#...#...#.#.#.....#.#.#.....#.#.#.#...#.#...#...#.#.....#.#.......#...#...##
|
||||||
|
#.#.#.#.#########.#.#.#.#.#.#.###.#.#####.#.#.###.###.#.#.#.###.###.###.#.#.###.#.###############.##
|
||||||
|
#.#...#.#.#.......#.#.#.#.#...#...#...#...#.#...#...#...#...#.....#.....#...#...#.....#...........##
|
||||||
|
#.#####.#.#.#####.#.###.#.#####.#####.#.###.#.#.###.###.#######.#.###.#######.#######.#.###.#####.##
|
||||||
|
#.....#.#.#.#...#.#.....#.......#.....#...#...#.#.#...#.#.....#.#...#.#.....#.......#.#.#...#...#.##
|
||||||
|
#####.#.#.#.#.#.#.#####.#########.###.###.#####.#.#.###.#.###.#####.#.#.###.#.#.#####.#.#.###.###.##
|
||||||
|
#.....#...#.#.#.....#...#.........#.#...#.........#.#...#.#.#.#...#.#.#...#.#.#...#...#.#.#...#...##
|
||||||
|
#.###.###.#.#.#######.#######.#.###.###.###########.#.###.#.#.#.#.#.###.###.#####.#.#####.###.#.####
|
||||||
|
#...#...#.#.#...#.....#.....#.#.#...#...#.......#...#.....#.#.#.#...#...#...#...#.#...#...#...#...##
|
||||||
|
#.#.#.###.#.#####.#######.#.###.#.#.#.#####.#.#.#.#########.#.#.#####.###.###.#.#.###.#.###.#####.##
|
||||||
|
#.#.#.#...#.....#.........#.....#.#.#.....#.#.#.#...#.........#...#...#...#...#.#...#...#.......#.##
|
||||||
|
###.#.#.#######.###################.#####.###.#####.#.###########.#.###.#####.#.###.#####.#####.#.##
|
||||||
|
#...#.#.#.......#.....#.........#.......#.....#.....#...#.#.....#.....#.#.....#.........#.#...#...##
|
||||||
|
#.#####.#.#.#####.#.#.#.###.###.#.###########.#.###.###.#.#.#.#.#####.#.#.#########.#####.#.########
|
||||||
|
#.......#.#.#.....#.#.#.#.#.#.....#...#.....#.#.#...#...#...#.#.....#.#.#.#.......#.#.....#.......##
|
||||||
|
#.#######.###.#####.###.#.#.#######.#.#.#.###.#.#####.#######.#####.###.#.#.#####.###.###########.##
|
||||||
|
#.......#.........#.......#.........#...#.....#...............#.........#.......#................E##
|
||||||
|
####################################################################################################
|
||||||
|
####################################################################################################
|
||||||
1
nikolaevda/test file
Normal file
1
nikolaevda/test file
Normal file
|
|
@ -0,0 +1 @@
|
||||||
|
print("hello,world!")
|
||||||
Loading…
Reference in New Issue
Block a user