如何在O(1)中为LinkedStack编写pop()
方法?
我的LinkedStack
课程中有两位私人数据成员:ListNode* head
和ListNode* tail
。
head
指向LinkedStack
的开头,tail
指向LinkedStack
的结尾。
pop()
将移除ListNode
指向的tail
,然后tail
将指向之前<{>}的ListNode
> tail
。
了解这一点,我将如何在pop()
中撰写O(1)
?显然,我可以编写一个for循环,在ListNode
之前抓住之前的tail
,但pop()
不会O(1)
。
由于这是作业,我不是在寻找代码解决方案,只是提示正确的方向。
编辑:我可能看到的一个解决方案是拥有ListNode* prev
数据成员,该成员始终指向tail
之前的前一个ListNode。但我觉得这是一种更有效的方式......
Edit2 :谢谢@ user4581301。 假设pop()
为空时不会调用LinkedStack
。
答案 0 :(得分:3)
正如您所述,任何情况,您必须遍历列表以找到特定元素,这将使得无法满足常量时间要求。这包括一个单链表,您可以将项目推送到最后。 双向链接列表将更容易,因为您可以从尾部到倒数第二项而不进行遍历。
但是,我不确定为什么你要推到最后。如果您要在列表的前面上推送新元素,那么push
和pop
实现固定时间是微不足道的。
就此而言,我的意思是(伪代码,正如你所提到的,&#34;这是作业和#34;):
def push(x):
allocate node # get new node and set data.
node.data = x
node.next = head # insert at head of list
head = node
def pop():
assert head != null # catch pop on empty stack
node = head # get first node and data
retval = node.data
head = head.next # set head to be second node
free node # free node and return data
return retval
您可以看到任何操作都没有遍历列表。首先,将7
推送到一堆素数:
Starting list:
head
\
5 -> 3 -> 2 -|
Create new node, point to current head:
head
\
7 -> 5 -> 3 -> 2 -|
Point head at new node:
head
\
7 -> 5 -> 3 -> 2 -|
现在让我们弹出同样的价值。
Starting list:
head
\
7 -> 5 -> 3 -> 2 -|
Save head as node, and value to return (7):
head
\
7 -> 5 -> 3 -> 2 -|
/
node
Adjust head:
head
\
7 -> 5 -> 3 -> 2 -|
/
node
Free node and return stored value (7):
head
\
5 -> 3 -> 2 -|