class LinkedList_Test_Remove_Duplicates_With_0_Elements(unittest.TestCase):
    
    def setUp(self):
        self._linkedList = LinkedList()
    
    def test_remove_duplicate_of_empty_list(self):
        self._linkedList.remove_duplicates()
        
    def tearDown(self):
        self._linkedList = None
class LinkedList_Test_Remove_Duplicates_With_2_Identical_Elements(unittest.TestCase):
    
    def setUp(self):
        self._linkedList = LinkedList()
        element_to_append = 1
        self._linkedList.append(element_to_append)
        self._linkedList.append(element_to_append)
        
    def test_remove_duplicates_of_list_with_2_identical_elements(self):
        old_head = self._linkedList.head
        expected_tail = old_head
        
        self._linkedList.remove_duplicates()
        expected_length = 1
        self.assertEqual(self._linkedList.length, expected_length, 'Linked list length did not add up after removing duplicates')
        self.assertEqual(self._linkedList.head, old_head, 'Linked list head did not add up after removing duplicates')
        self.assertEqual(self._linkedList.tail, expected_tail, 'Linked list tail did not add up after removing duplicates')
        
    def tearDown(self):
        self._linkedList = None
class LinkedList_Test_Remove_Duplicates_With_Duplicates_At_Middle(unittest.TestCase):
    
    def setUp(self):
        #build [2, 1, 1, 1, 3]
        self._linkedList = LinkedList()
        self._linkedList.append(2)
        element_to_append = 1
        self._linkedList.extend([element_to_append, element_to_append, element_to_append])
        self._linkedList.append(3)
        
    def test_remove_duplicates_of_list_with_2_duplicates_in_Middle(self):
        expected_head = self._linkedList._head
        expected_tail = self._linkedList._tail
        
        self._linkedList.remove_duplicates()
        expected_length = 3
        self.assertEqual(self._linkedList.length, expected_length, 'Linked list length did not add up after removing duplicates')
        self.assertEqual(self._linkedList._head, expected_head, 'Linked list head did not add up after removing duplicates')
        self.assertEqual(self._linkedList._tail, expected_tail, 'Linked list tail did not add up after removing duplicates')
        
    def tearDown(self):
        self._linkedList = None
class LinkedList_Test_Remove_Duplicates_With_Duplicates_At_Tail(unittest.TestCase):
    
    def setUp(self):
        #build [2, 1, 1, 1]
        self._linkedList = LinkedList()
        self._linkedList.append(2)
        element_to_append = 1
        self._linkedList.extend([element_to_append, element_to_append, element_to_append])
        
    def test_remove_duplicates_of_list_with_2_identical_elements(self):
        expected_head = self._linkedList._head
        expected_tail = self._linkedList._head.next_node
        
        self._linkedList.remove_duplicates()
        expected_length = 2
        #compare references of head and tail
        self.assertEqual(self._linkedList.length, expected_length, 'Linked list length did not add up after removing duplicates')
        self.assertEqual(self._linkedList._head, expected_head, 'Linked list head did not add up after removing duplicates')
        self.assertEqual(self._linkedList._tail, expected_tail, 'Linked list tail did not add up after removing duplicates')
        
    def tearDown(self):
        self._linkedList = None
    #Lets delete 7
    print('Deleting 7')
    element_to_remove = 7
    link_list.remove(element_to_remove)

    #Try to find it.
    print('Trying to find %s' % str(element_to_remove))
    index_of_deleted = link_list.index(element_to_remove)
    print('Index of deleted element is %s' % str(index_of_deleted))
    #print list again
    print_list(link_list)

    #
    #Lets insert 7 at index 5
    print('Insert 7 into the list at index 4')
    element_to_insert = 7
    index_at = 5
    link_list.insert_at(index=index_at, element=element_to_insert)
    print_list(link_list)

    # Removing duplicates
    print('Removing duplicates')
    link_list = LinkedList()
    link_list.extend([1, 1, 2, 3, 4, 4, 5, 6, 6, 7, 8, 9, 10, 10])
    print_list(link_list)
    link_list.remove_duplicates()
    print_list(link_list)

    #Reverse print list using reversed
    print_reverse_list(link_list)