我正在使用python中的循环链接列表来实现Queue的实现。以下是循环LinkedList的图形表示
除了出队例程,我能够实现大多数代码。在出队例程中,必须跟踪相对于当前节点的上一个节点参考以及下一个节点参考。在双链表中,很容易实现。但是,我不知道如何在单个链接列表中实现此概念。
class CircularQueue:
''' Queue implementation using a Circularly linked list for storage '''
class _Node:
__slots__ == '_element','_next'
def __init__(self,element,next):
self._element = element
self._next = next
def __init__(self):
'''Create an empty queue'''
self._current = None
self._size = 0
def __len__(self):
return self._size
def is_empty(self):
return self._size == 0
def enqueue(self,e):
node = self._Node(e,None)
if self.is_empty():
newest._next = newest
else:
curr_node = self._current._next
node._next = curr_node
self._current = node
self._size += 1
def dequeue(self):
if self.is_empty():
raise Empty('Stack is empty')
如果有人可以给我关于如何在出队例程中前进的想法,这会更有帮助。
答案 0 :(得分:0)
由于链接列表是单向的,因此元素仅引用了它的后继元素,而从未引用过它的前任元素,为了使列表中的元素出队容易,您需要同时使用这两个元素。
我看到两种可能性:您可以使链表成为双向的,因此可以添加对前一个元素的引用。我对您的实现进行了一些整理,希望您仍然可以这样做:
""" Queue implementation using a Circularly linked list for storage """
class _Node:
def __init__(self, element, next=None, previous=None):
self.element = element
if next is None:
next = self
self.next = next
if previous is None:
previous = self
self.previous = previous
class CircularQueue:
def __init__(self):
self._current = None
self._size = 0
def __len__(self):
return self._size
def get_head(self):
return self._current.element
def is_empty(self):
return self._size == 0
def next(self):
self._current = self._current.next
return self._current.element
def previous(self):
self._current = self._current.pevious
return self._current
def enqueue(self, element):
""" Adds an element at the current position, ahead of the current element """
if self.is_empty():
new_node = _Node(element)
else:
new_node = _Node(element, self._current.next, self._current)
self._current.next = new_node
self._current = new_node
self._size += 1
我们现在可以检查我们的代码是否正确:
cq = CircularQueue()
cq.enqueue("A")
cq.enqueue("B")
cq.enqueue("C")
print(cq.get_head())
print(cq.next())
print(cq.next())
print(cq.next())
然后您将看到C,A,B和C连续打印。
双边队列使我们能够实现这样的出队方法:
def dequeue(self, element_key=None):
if self.is_empty():
raise KeyError('Stack is empty')
if element_key is None:
self._current.next.previous = self._current.previous
self._current.previous.next = self._current.next
return self.next()
else:
current = self._current
while self._current.element != element_key:
self.next()
if self._current == current:
raise KeyError('Element not found')
self.dequeue()
如果我们对其进行测试...
print("dequeuing 'B'")
cq.dequeue("B")
print(cq.get_head())
print(cq.next())
print(cq.next())
print(cq.next())
...我们应该看到打印了“使'B'出队”,以及C,A,C和A再次被打印,这使我们感到高兴。 :)
也可以使用单方面的方法;您可能会花很少的时间来处理参考,而您会遍历整个圈子(在最坏的情况下)。首先,您将跳到队列中的下一个元素,直到当前元素的下一个元素是您要出队的元素,然后将当前元素的下一个引用设置为已出队的下一个元素,基本上已经完成。>