Python中的双链表
结果是一个错误,因为超过了时间限制, 但我已经提出了停止迭代 我认为我在迭代部分做了一些错误的事情,但是很难找到错误。测试输出保持运行,甚至打印出None值。这是怎么发生的Python中的双链表,python,python-3.x,Python,Python 3.x,结果是一个错误,因为超过了时间限制, 但我已经提出了停止迭代 我认为我在迭代部分做了一些错误的事情,但是很难找到错误。测试输出保持运行,甚至打印出None值。这是怎么发生的 class LinkedListIterator: def __init__(self, head): self.__current = head.get_next() def __iter__(self): return self def __next__(sel
class LinkedListIterator:
def __init__(self, head):
self.__current = head.get_next()
def __iter__(self):
return self
def __next__(self):
if self.__current == None:
raise StopIteration
else:
item = self.__current.get_data()
self.__current = self.__current.get_next()
return item
这些是我用来运行程序的输入:
my_list = LinkedListDLL()
my_list.add_to_head(1)
print("Contents:", end=" ")
for node in my_list:
print(node, end=" ")
print()
此代码用于在迭代到达列表的顶部时停止迭代
if self.__current == None:
raise StopIteration
但是,您用一个nodedell
对象表示头部,该对象不同于None
您可以保留对头部的引用,并对照该引用进行检查:
class LinkedListIterator:
def __init__(self, head):
self._head = head
self._current = head.get_next()
def __iter__(self):
return self
def __next__(self):
if self._current is self._head:
raise StopIteration
else:
item = self._current.get_data()
self._current = self._current.get_next()
return item
您想要实现的是带有双链表实现的
MutableSequence
的API
要在Python中实现这一点,您应该依赖于collections.abc
,它可以指导您完成实现所有必需方法的过程
例如,链表实际上是从MutableSequence
继承的类
from collections.abc import MutableSequence
class LinkedList(MutableSequence):
pass
ll = LinkedList()
在实例化一个包含一些尚未编写的抽象方法的类时,您将得到一个TypeError
,它将指导您完成需要实现哪些方法
TypeError: Can't instantiate abstract class LinkedList with abstract methods __delitem__, __getitem__, __len__, __setitem__, insert
特别要注意的是,列表
或链表不是迭代器,而是iterable。这意味着\uuuuu iter\uuuuu
方法不应返回self
,而应依赖\uuuu next\uuuuuu
,而应返回链接列表内容上的全新迭代器
换句话说,您只能通过迭代器进行一次迭代,并且可以通过和iterable进行多次迭代
全面实施
事实证明,我有一个完整的双链表实现,就是这样实现的。你可以看看
from collections.abc import MutableSequence
class LinkedList(MutableSequence):
class _Node:
def __init__(self, value, _next=None, _last=None):
self.value, self._next, self._last = value, _next, _last
def __str__(self):
return f'Node({self.value})'
def __init__(self, iterable=()):
self.start = None
self.last = None
empty = object()
iterable = iter(iterable)
first = next(iterable, empty)
if first is empty:
return
current = self._Node(first)
self.start, self.last = current, current
for value in iterable:
new_node = self._Node(value, _last=self.last)
self.last._next = new_node
self.last = new_node
def __len__(self):
if self.start is None:
return 0
else:
return sum(1 for _ in self)
def __iter_nodes(self):
current = self.start
while current is not None:
yield current
current = current._next
def __reversed_iter_nodes(self):
current = self.last
while current is not None:
yield current
current = current._last
def __iter__(self):
for node in self.__iter_nodes():
yield node.value
def __reversed__(self):
for node in self.__reversed_iter_nodes():
yield node.value
def __get_node(self, index):
if index >= 0:
for item in self.__iter_nodes():
if index == 0:
return item
index -= 1
else:
for item in self.__reversed_iter_nodes():
if index == 0:
return item
index += 1
raise IndexError
def __getitem__(self, index):
if index >= 0:
for item in self:
if index == 0:
return item.value
index -= 1
else:
for item in reversed(self):
if index == 0:
return item.value
index += 1
raise IndexError
def __setitem__(self, key, value):
self[key].value = value
def __delitem__(self, key):
node = self[key]
if node._last:
node._last._next = node._next
if node._next:
node._next._last = node._last
def insert(self, index, value):
if index > len(self):
self.last = self._Node(value, _last=self.last)
else:
where = self.__get_node(index)
_last = where._last
new_node = self._Node(value, _next=where, _last=_last)
if _last:
_last._next = new_node
else:
self.start = new_node
where._last = new_node
例子
输出
你的节点类是如何定义的?请用你的
nodedell
类的类定义更新你的问题,以便它可以正确缩进。是的,我已经为我的编码上传了更详细的内容。你可以像你为LinkedListerator
所做的那样,将代码复制并粘贴为文本,而不是将其作为图片发布,所以我们可以很容易地运行它并自己尝试它?哦,很抱歉。。。这是我第一次使用这个网站
ll = LinkedList(range(1, 5))
print(*ll)
print(*reversed(ll))
ll.insert(2, 'foo')
print(*ll)
1 2 3 4
4 3 2 1
1 2 foo 3 4