import csv import random import sys import time import threading sys.setrecursionlimit(30000) threading.stack_size(64*1024*1024) def ll_insert(head, name, phone): """Добавляет запись или обновляет телефон, если имя уже существует. Возвращает новую голову списка.""" curr = head while curr is not None: if curr["name"] == name: curr["phone"] = phone return head curr = curr["next"] new_node = {"name": name, "phone": phone, "next": head} return new_node def ll_find(head, name): """Ищет узел по имени. Возвращает телефон или None.""" curr = head while curr is not None: if curr["name"] == name: return curr["phone"] curr = curr["next"] return None def ll_delete(head, name): """Удаляет узел по имени. Возвращает новую голову списка.""" curr = head prev = None while curr is not None: if curr["name"] == name: if prev is None: return curr["next"] else: prev["next"] = curr["next"] return head prev = curr curr = curr["next"] return head def ll_list_all(head): """Собирает все записи в список и сортирует их по имени.""" records = [] curr = head while curr is not None: records.append((curr["name"], curr["phone"])) curr = curr["next"] records.sort(key=lambda x: x[0]) return records def ht_create(size=1000): """Создает пустую хеш-таблицу заданного размера.""" return [None] * size def ht_insert(buckets, name, phone): """Вычисляет индекс бакета и вызывает ll_insert.""" idx = abs(hash(name)) % len(buckets) buckets[idx] = ll_insert(buckets[idx], name, phone) def ht_find(buckets, name): """Вычисляет индекс бакета и вызывает ll_find.""" idx = abs(hash(name)) % len(buckets) return ll_find(buckets[idx], name) def ht_delete(buckets, name): """Вычисляет индекс бакета и вызывает ll_delete.""" idx = abs(hash(name)) % len(buckets) buckets[idx] = ll_delete(buckets[idx], name) def ht_list_all(buckets): """Собирает записи из всех бакетов и сортирует их по имени.""" records = [] for head in buckets: curr = head while curr is not None: records.append((curr["name"], curr["phone"])) curr = curr["next"] records.sort(key=lambda x: x[0]) return records def bst_insert(root, name, phone): """Рекурсивно вставляет узел или обновляет телефон.""" if root is None: return {"name": name, "phone": phone, "left": None, "right": None} if name == root["name"]: root["phone"] = phone elif name < root["name"]: root["left"] = bst_insert(root["left"], name, phone) else: root["right"] = bst_insert(root["right"], name, phone) return root def bst_find(root, name): """Рекурсивный поиск по дереву.""" if root is None: return None if name == root["name"]: return root["phone"] elif name < root["name"]: return bst_find(root["left"], name) else: return bst_find(root["right"], name) def bst_delete(root, name): """Рекурсивное удаление узла из BST.""" 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: return root["right"] if root["right"] is None: return root["left"] min_node = root["right"] while min_node["left"] is not None: min_node = min_node["left"] root["name"] = min_node["name"] root["phone"] = min_node["phone"] root["right"] = bst_delete(root["right"], min_node["name"]) return root def bst_list_all(root): """Центрированный обход дерева для сбора записей.""" records = [] def _inorder(node): if node is not None: _inorder(node["left"]) records.append((node["name"], node["phone"])) _inorder(node["right"]) _inorder(root) return records