62 lines
1.8 KiB
Python
62 lines
1.8 KiB
Python
from dataclasses import dataclass
|
|
from typing import Iterator, Optional
|
|
|
|
@dataclass
|
|
class Node[T]:
|
|
value: T
|
|
next_node: Optional['Node[T]']
|
|
|
|
|
|
@dataclass
|
|
class LinkedList[T]:
|
|
|
|
def __post_init__(self):
|
|
self.__head: Optional[Node[T]] = None
|
|
self.__length = 0
|
|
|
|
def __eq__(self, other: 'LinkedList[T]') -> bool:
|
|
if len(self) != len(other):
|
|
return False
|
|
for i in range(0, len(self)):
|
|
if self[i] != other[i]:
|
|
return False
|
|
return True
|
|
|
|
def __iter__(self) -> Iterator[T]:
|
|
node = self.__head
|
|
while node:
|
|
yield node.value
|
|
node = node.next_node
|
|
|
|
def append(self, value: T):
|
|
if not self.__head:
|
|
self.__head = Node(value, None)
|
|
else:
|
|
node = self.__head
|
|
while node.next_node:
|
|
node = node.next_node
|
|
node.next_node = Node(value, None)
|
|
self.__length += 1
|
|
|
|
def remove(self, value: T):
|
|
if self.__head and self.__head.value == value:
|
|
self.__head = self.__head.next_node
|
|
self.__length -= 1
|
|
elif self.__head:
|
|
node = self.__head
|
|
while node.next_node and node.next_node.value != value:
|
|
node = node.next_node
|
|
if node.next_node and node.next_node.value == value:
|
|
node.next_node = node.next_node.next_node
|
|
self.__length -= 1
|
|
|
|
def __len__(self) -> int:
|
|
return self.__length
|
|
|
|
def __getitem__(self, index: int) -> T:
|
|
if index >= len(self):
|
|
raise IndexError
|
|
node = self.__head
|
|
for _ in range(0, index):
|
|
node = node.next_node
|
|
return node.value |