def test_print_traversals(self): # WARNING: Tests are for Print() # Debug calls to Print() in functions will cause failure stdout_ = sys.stdout # Keep previous value sys.stdout = io.StringIO() self.bst = BSTNode(1) self.bst.insert(8) self.bst.insert(5) self.bst.insert(7) self.bst.insert(6) self.bst.insert(3) self.bst.insert(4) self.bst.insert(2) self.bst.in_order_print(self.bst) output = sys.stdout.getvalue() self.assertEqual(output, "1\n2\n3\n4\n5\n6\n7\n8\n") sys.stdout = io.StringIO() self.bst.bft_print(self.bst) output = sys.stdout.getvalue() self.assertTrue(output == "1\n8\n5\n3\n7\n2\n4\n6\n" or output == "1\n8\n5\n7\n3\n6\n4\n2\n") sys.stdout = io.StringIO() self.bst.dft_print(self.bst) output = sys.stdout.getvalue() self.assertTrue(output == "1\n8\n5\n7\n6\n3\n4\n2\n" or output == "1\n8\n5\n3\n2\n4\n7\n6\n")
def find_middle(start_ptr, end_ptr, bst): counter = 0 current = start_ptr prev = None while current is not end_ptr: counter += 1 prev = current current = current.next_node half = int(counter / 2) counter = 0 current = start_ptr prev = None while counter != half: counter += 1 prev = current current = current.next_node if bst is None: bst = BSTNode(current.value) else: bst.insert(current.value) left_start = start_ptr left_end = prev right_start = current.next_node right_end = end_ptr bst = find_middle(left_start, current, bst) bst = find_middle(current, right_end, bst) return bst
def binary_search(lst, lst2): bst = BST(names_1[0]) for i in range(len(names_1)): if i != 0: bst.insert(names_1[i]) for name_2 in names_2: if bst.contains(name_2): duplicates.append(name_2)
def binary_search_tree_approach(): duplicates = [] # insert one of the lists into a binary search tree # uses the binary search tree class we built earlier this week bst = BSTNode(names_2[0]) for name in names_2: bst.insert(name) # search bst for matching names for name in names_1: if bst.contains(name): duplicates.append(name) return duplicates
def test_WideAllNodes(self): self.assertEqual( [node.NodeKey for node in list(self.tree.WideAllNodes())], [8, 4, 12, 2, 6, 10, 14, 1, 3, 5, 7, 9, 11, 13, 15]) self.tree = BST(BSTNode(8, 80, None)) self.assertEqual( [node.NodeKey for node in list(self.tree.DeepAllNodes(0))], [8])
def test_DeepAllNodes(self): # проверка in-order self.assertEqual( [node.NodeKey for node in list(self.tree.DeepAllNodes(0))], [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]) self.tree = BST(BSTNode(8, 80, None)) self.assertEqual( [node.NodeKey for node in list(self.tree.DeepAllNodes(0))], [8])
def test_DeepAllNodes(self): # проверка post-order self.assertEqual( [node.NodeKey for node in list(self.tree.DeepAllNodes(1))], [1, 3, 2, 5, 7, 6, 4, 9, 11, 10, 13, 15, 14, 12, 8]) self.tree = BST(BSTNode(8, 80, None)) self.assertEqual( [node.NodeKey for node in list(self.tree.DeepAllNodes(0))], [8])
def bst_ordered(n, target): bst = BSTNode(0) # Overall for the next two lines O(n^2) for i in range(1, n): # O(n) bst.insert(i) # O(n) bst.contains(target) # O(n)
def bst_random(random_nums, target): bst = BSTNode(random_nums[0]) # O(1) # overall: n log n for num in random_nums[1:]: # iteration ->O(n) bst.insert(num) # insert is O(log n) bst.contains(target) # O(log n) -> with each iteration you can throw out each item you are looking at
class BinarySearchTreeTests(unittest.TestCase): def setUp(self): self.bst = BSTNode(5) def test_insert(self): self.bst.insert(2) self.bst.insert(3) self.bst.insert(7) self.bst.insert(6) self.assertEqual(self.bst.left.right.value, 3) self.assertEqual(self.bst.right.left.value, 6) # def test_handle_dupe_insert(self): # self.bst2 = BSTNode(1) # self.bst2.insert(1) # self.assertEqual(self.bst2.right.value, 1) def test_contains(self): self.bst.insert(2) self.bst.insert(3) self.bst.insert(7) self.assertTrue(self.bst.contains(7)) self.assertFalse(self.bst.contains(8))
class BinarySearchTreeTest(unittest.TestCase): def setUp(self): self.root = BSTNode(5) def test_inserts_lower_to_left(self): self.root.insert(4) self.assertEqual(self.root.left.value, 4) def test_inserts_higher_to_right(self): self.root.insert(6) self.assertEqual(self.root.right.value, 6) def test_deep_insertion_path(self): self.root.insert(2) self.root.insert(4) self.root.insert(3) self.assertEqual(self.root.left.right.left.value, 3)
class Tree: def __init__(self): self.root = None def insert(self, value): if self.root: return self.root.insert(value) else: self.root = BSTNode(value) return True def find(self, value): if self.root: return self.root.contains(value) else: return False
def setUp(self): # Создание дерева из 15 злементов начиная от корня (8) self.tree = BST(BSTNode(8, 80, None)) self.tree.AddKeyValue(4, 40) self.tree.AddKeyValue(12, 120) self.tree.AddKeyValue(2, 20) self.tree.AddKeyValue(6, 60) self.tree.AddKeyValue(10, 100) self.tree.AddKeyValue(14, 140) self.tree.AddKeyValue(1, 10) self.tree.AddKeyValue(3, 30) self.tree.AddKeyValue(5, 50) self.tree.AddKeyValue(7, 70) self.tree.AddKeyValue(9, 90) self.tree.AddKeyValue(11, 110) self.tree.AddKeyValue(13, 130) self.tree.AddKeyValue(15, 150)
class BinarySearchTreeTests(unittest.TestCase): def setUp(self): self.bst = BSTNode(5) def test_insert(self): self.bst.insert(2) self.bst.insert(3) self.bst.insert(7) self.bst.insert(6) self.assertEqual(self.bst.left.right.value, 3) self.assertEqual(self.bst.right.left.value, 6) def test_handle_dupe_insert(self): self.bst2 = BSTNode(1) self.bst2.insert(1) self.assertEqual(self.bst2.right.value, 1)
def setUp(self): self.bst = BSTNode(5)
class BinarySearchTreeTests(unittest.TestCase): def setUp(self): self.bst = BSTNode(5) def test_insert(self): self.bst.insert(2) self.bst.insert(3) self.bst.insert(7) self.bst.insert(6) self.assertEqual(self.bst.left.right.value, 3) self.assertEqual(self.bst.right.left.value, 6) def test_handle_dupe_insert(self): self.bst2 = BSTNode(1) self.bst2.insert(1) self.assertEqual(self.bst2.right.value, 1) def test_contains(self): self.bst.insert(2) self.bst.insert(3) self.bst.insert(7) self.assertTrue(self.bst.contains(7)) self.assertFalse(self.bst.contains(8)) def test_get_max(self): self.assertEqual(self.bst.get_max(), 5) self.bst.insert(30) self.assertEqual(self.bst.get_max(), 30) self.bst.insert(300) self.bst.insert(3) self.assertEqual(self.bst.get_max(), 300) def test_for_each(self): arr = [] cb = lambda x: arr.append(x) v1 = random.randint(1, 101) v2 = random.randint(1, 101) v3 = random.randint(1, 101) v4 = random.randint(1, 101) v5 = random.randint(1, 101) self.bst.insert(v1) self.bst.insert(v2) self.bst.insert(v3) self.bst.insert(v4) self.bst.insert(v5) self.bst.for_each(cb) self.assertTrue(5 in arr) self.assertTrue(v1 in arr) self.assertTrue(v2 in arr) self.assertTrue(v3 in arr) self.assertTrue(v4 in arr) self.assertTrue(v5 in arr) def test_print_traversals(self): # WARNING: Tests are for Print() # Debug calls to Print() in functions will cause failure stdout_ = sys.stdout # Keep previous value sys.stdout = io.StringIO() self.bst = BSTNode(1) self.bst.insert(8) self.bst.insert(5) self.bst.insert(7) self.bst.insert(6) self.bst.insert(3) self.bst.insert(4) self.bst.insert(2) self.bst.in_order_print(self.bst) output = sys.stdout.getvalue() self.assertEqual(output, "1\n2\n3\n4\n5\n6\n7\n8\n") sys.stdout = io.StringIO() self.bst.bft_print(self.bst) output = sys.stdout.getvalue() self.assertTrue(output == "1\n8\n5\n3\n7\n2\n4\n6\n" or output == "1\n8\n5\n7\n3\n6\n4\n2\n") sys.stdout = io.StringIO() self.bst.dft_print(self.bst) output = sys.stdout.getvalue() self.assertTrue(output == "1\n8\n5\n7\n6\n3\n4\n2\n" or output == "1\n8\n5\n3\n2\n4\n7\n6\n") sys.stdout = io.StringIO() self.bst.pre_order_dft(self.bst) output = sys.stdout.getvalue() self.assertEqual(output, "1\n8\n5\n3\n2\n4\n7\n6\n") sys.stdout = io.StringIO() self.bst.post_order_dft(self.bst) output = sys.stdout.getvalue() self.assertEqual(output, "2\n4\n3\n6\n7\n5\n8\n1\n") sys.stdout = stdout_ # Restore stdout
def test_handle_dupe_insert(self): self.bst2 = BSTNode(1) self.bst2.insert(1) self.assertEqual(self.bst2.right.value, 1)
names_1 = f.read().split("\n") # List containing 10000 names f.close() f = open('names_2.txt', 'r') names_2 = f.read().split("\n") # List containing 10000 names f.close() duplicates = [] # Return the list of duplicates in this data structure # Replace the nested for loops below with your improvements # for name_1 in names_1: # for name_2 in names_2: # if name_1 == name_2: # duplicates.append(name_1) bst = BSTNode("NOT TARGET") for i in names_2: bst.insert(i) for i in names_1: if bst.contains(i): duplicates.append(i) print(f"---\n---") # while not queue.size == len(names_1) - 1: # queue.enqueue(names_1[queue.size]) # current_node = queue.storage.head
f = open('names/names_2.txt', 'r') names_2 = f.read().split("\n") # List containing 10000 names f.close() # making the 2nd list a set to remove duplicates so that # we don't have to traverse over copies # names_1 = set(names_1) names_2 = set(names_2) # runtime for this seems to be O(n log n) # because it isn't constant but doesn't exponentially increase # based on the size of the lists duplicates = [] # Return the list of duplicates in this data structure # creating the root node of the tree with the first value of names_1 tree = BSTNode(names_1[0]) # using the insert method to put the rest of the names_1 list to the tree for name in names_1[1:]: tree.insert(name) # checking the 2nd list with the contains method from the tree to for name in names_2: if tree.contains(name): # if the contains method duplicates.append(name) # Replace the nested for loops below with your improvements # for name_1 in names_1: # if name_1 in names_2: # duplicates.append(name_1) end_time = time.time()
start_time = time.time() f = open('names_1.txt', 'r') names_1 = f.read().split("\n") # List containing 10000 names f.close() f = open('names_2.txt', 'r') names_2 = f.read().split("\n") # List containing 10000 names f.close() # Return the list of duplicates in this data structure # duplicates = [name for name in names_1 if name in names_2] duplicates = [] bst = BSTNode('testing') # # Not quite sure how else to accomplish this at the moment # # OPTIMIZED TO RUN IN 0.172 SECONDS ON MY MACHINE # # for each name in names_1 for name in names_1: # O(n) # add that name to the binary search tree bst.insert(name) # for each name in names 2 for name in names_2: # see if that name is already in the bst if bst.contains(name): # if it is, append it to the duplicates array duplicates.append(name)
import time from binary_search_tree import BSTNode start_time = time.time() f = open('names_1.txt', 'r') names_1 = f.read().split("\n") # List containing 10000 names f.close() f = open('names_2.txt', 'r') names_2 = f.read().split("\n") # List containing 10000 names f.close() duplicates = [] # Return the list of duplicates in this data structure bst = BSTNode("Dan") for name in names_1: bst.insert(name) for name in names_2: if bst.contains(name): duplicates.append(name) # Replace the nested for loops below with your improvements # for name_1 in names_1: # for name_2 in names_2: # if name_1 == name_2: # duplicates.append(name_1) end_time = time.time() print(f"{len(duplicates)} duplicates:\n\n{', '.join(duplicates)}\n\n")
names_1 = f.read().split("\n") # List containing 10000 names f.close() f = open('names_2.txt', 'r') names_2 = f.read().split("\n") # List containing 10000 names f.close() duplicates = [] # Return the list of duplicates in this data structure # Replace the nested for loops below with your improvements # for name_1 in names_1: # for name_2 in names_2: # if name_1 == name_2: # duplicates.append(name_1) nodes = BSTNode('names') for names in names_1: nodes.insert(names) for name in names_2: if nodes.contains(name): duplicates.append(name) end_time = time.time() print(f"{len(duplicates)} duplicates:\n\n{', '.join(duplicates)}\n\n") print(f"runtime: {end_time - start_time} seconds") # ---------- Stretch Goal ----------- # Python has built-in tools that allow for a very efficient approach to this problem # What's the best time you can accomplish? Thare are no restrictions on techniques or data
names_1 = f.read().split("\n") # List containing 10000 names f.close() f = open('names_2.txt', 'r') names_2 = f.read().split("\n") # List containing 10000 names f.close() duplicates = [] # Return the list of duplicates in this data structure # Replace the nested for loops below with your improvements # for name_1 in names_1: # for name_2 in names_2: # if name_1 == name_2: # duplicates.append(name_1) bst1 = BSTNode(names_1[0]) for name_1 in names_1[1:]: bst1.insert(name_1) for name_2 in names_2: if bst1.contains(name_2): duplicates.append(name_2) # if name_1 == name_2: # duplicates.append(name_1) end_time = time.time() print(f"{len(duplicates)} duplicates:\n\n{', '.join(duplicates)}\n\n") print(f"runtime: {end_time - start_time} seconds") # ---------- Stretch Goal ----------- # Python has built-in tools that allow for a very efficient approach to this problem # What's the best time you can accomplish? Thare are no restrictions on techniques or data
f.close() duplicates = [] # Return the list of duplicates in this data structure """ # Replace the nested for loops below with your improvements for name_1 in names_1: for name_2 in names_2: if name_1 == name_2: duplicates.append(name_1) The runtime was: 10.852504014968872 seconds """ # Create a BST for names_1 bst_1 = BSTNode(names_1[0]) # For range from the second item in names_1 till the rest of it's length for i in range(1, len(names_1)): # Add every other item to bst_1 bst_1.insert(names_1[i]) # For range from 0 till the end og names_2 for i in range(0, len(names_2)): # Compare items in bst_1 to names_2 # If bst contains the name in index i if bst_1.contains(names_2[i]): # Store that name in duplicates duplicates.append(names_2[i]) end_time = time.time()
from binary_search_tree import BSTNode import time start_time = time.time() f = open('names_1.txt', 'r') names_1 = f.read().split("\n") # List containing 10000 names f.close() f = open('names_2.txt', 'r') names_2 = f.read().split("\n") # List containing 10000 names f.close() duplicates = [] # Return the list of duplicates in this data structure tree = BSTNode("Andrew Sitzes") for names in names_1: tree.insert(names) for checkNames in names_2: if tree.contains(checkNames): duplicates.append(checkNames) # Replace the nested for loops below with your improvements # for name_1 in names_1: # for name_2 in names_2: # if name_1 == name_2: # duplicates.append(name_1) end_time = time.time() print(f"{len(duplicates)} duplicates:\n\n{', '.join(duplicates)}\n\n")
def test_handle_dupe_insert(self): self.bst2 = BinarySearchTree(1) self.bst2.insert(1) self.assertEqual(self.bst2.right.value, 1)
''' Runtime of 10.86 seconds. Runtime is O(n^2) - Quadratic time Nested loops take as long as the length of list 1 * the length of list 2 ''' # # Replace the nested for loops below with your improvements # for name_1 in names_1: # for name_2 in names_2: # if name_1 == name_2: # duplicates.append(name_1) # Insert the names_1 data into a BST # Use the first name to create the root node of the BST tree = BSTNode(names_1[0]) # Insert the rest of the names into the existing BST for name in names_1: # O(n) to insert each each name from name_1 into the tree tree.insert(name) # Check to see if the tree contains the names from list 2 for name in names_2: # O(n) to go through each name in names_2 list # If the tree contains the name, append to duplicates list if tree.contains(name): # O(log n) to check if the tree contains the name duplicates.append(name) ''' Runtime of 0.17413 seconds. Runtime complexity is O(n log n) '''
def setUp(self): self.bst = BinarySearchTree(5)
python assigns numeric values to different letters as shown below: a = 'a' b = 'b' if a > b: print("true") else: print("false") We should be able to use the first letter of the name to determine where each name should be in a binary search tree. ''' duplicates = [] # Return the list of duplicates in this data structure binary_search_tree = BSTNode("root") for name_1 in names_1: binary_search_tree.insert(name_1) for name_2 in names_2: if binary_search_tree.contains(name_2): duplicates.append(name_2) # Improved runtime = 0.25955724716186523 seconds # Improved runtime complexity = O(2n) || 2n because 2 loops execute n times end_time = time.time() print(f"{len(duplicates)} duplicates:\n\n{', '.join(duplicates)}\n\n") print(f"runtime: {end_time - start_time} seconds")
def test_Count(self): # проверка подсчёта количества узлов дерева self.assertEqual(self.tree.Count(), 15) self.tree = BST(BSTNode(8, 80, None)) self.assertEqual(self.tree.Count(), 1)