A linked list is a linear data structure that consists of a sequence of nodes, where each node contains data and a reference (or link) to the next node in the sequence. Unlike arrays, linked lists do not require contiguous memory allocation, allowing for dynamic memory usage and efficient insertion and deletion operations.
the props of linked list:
Dynamic size: Linked lists can grow or shrink in size as needed, without the need for contiguous memory allocation.
Efficient insertion and deletion: Inserting or deleting a node in a linked list can be done in constant time O(1) if the reference to the node is known, as it only requires updating the links between nodes.
defremove(self, index): if index < 0or index >= self.__size: raise IndexError("Index out of bounds") if index == 0: self.__head = self.__head.next else: current = self.__head for _ inrange(index - 1): current = current.next current.next = current.next.next self.__size -= 1
defset(self, index, data): if index < 0or index >= self.__size: raise IndexError("Index out of bounds") current = self.__head for _ inrange(index): current = current.next current.data = data
defget(self, index): if index < 0or index >= self.__size: raise IndexError("Index out of bounds") current = self.__head for _ inrange(index): current = current.next return current.data
deffind(self, data): current = self.__head for index inrange(self.__size): if current.data == data: return index current = current.next return -1
defforEach(self, func): current = self.__head while current: func(current.data) current = current.next