import time import random import csv import os import sys sys.setrecursionlimit(30000) 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): curr = head while curr is not None: if curr['name'] == name: return curr['phone'] curr = curr['next'] return None def ll_delete(head, name): if head is None: return None if head['name'] == name: return head['next'] prev = head curr = head['next'] while curr is not None: if curr['name'] == name: prev['next'] = curr['next'] return head prev = curr curr = curr['next'] return head def ll_list_all(head): entries = [] curr = head while curr is not None: entries.append((curr['name'], curr['phone'])) curr = curr['next'] entries.sort(key=lambda x: x[0]) return entries def _hash(name, bucket_count): h = 0 for ch in name: h = (h * 31 + ord(ch)) % bucket_count return h def ht_create(bucket_count=2000): return [None] * bucket_count def ht_insert(buckets, name, phone): idx = _hash(name, len(buckets)) buckets[idx] = ll_insert(buckets[idx], name, phone) def ht_find(buckets, name): idx = _hash(name, len(buckets)) return ll_find(buckets[idx], name) def ht_delete(buckets, name): idx = _hash(name, len(buckets)) buckets[idx] = ll_delete(buckets[idx], name) def ht_list_all(buckets): entries = [] for head in buckets: curr = head while curr is not None: entries.append((curr['name'], curr['phone'])) curr = curr['next'] entries.sort(key=lambda x: x[0]) return entries def bst_insert(root, name, phone): new_node = {'name': name, 'phone': phone, 'left': None, 'right': None} if root is None: return new_node parent = None curr = root while curr is not None: parent = curr if name < curr['name']: curr = curr['left'] elif name > curr['name']: curr = curr['right'] else: curr['phone'] = phone return root if name < parent['name']: parent['left'] = new_node else: parent['right'] = new_node return root def bst_find(root, name): while root is not None: if name == root['name']: return root['phone'] elif name < root['name']: root = root['left'] else: root = root['right'] return None def _bst_min_node(node): while node and node['left'] is not None: node = node['left'] return node 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: return root['right'] if root['right'] is None: return root['left'] min_node = _bst_min_node(root['right']) 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): def inorder(node, res): if node is None: return inorder(node['left'], res) res.append((node['name'], node['phone'])) inorder(node['right'], res) result = [] inorder(root, result) return result