列表中的第一个和最后一个节点
有时用作列表中的第一个和最后一个节点
从未用作列表中的第一个和最后一个节点
维基百科说,
Sentinel节点是与链接一起使用的专门指定的节点 列表和树作为遍历路径终止符。一个哨兵节点 不保留或引用数据结构管理的任何数据。
我在想B,但我真的不知道。
答案 0 :(得分:1)
看,“Dummy”节点和“Sentinel”节点之间存在显着差异。
虚拟节点“有时会被用作列表中的第一个和最后一个节点”。
当您启动链表时,常见的方法是创建一个虚拟节点,有趣的是它是同时的最后一个节点。
显然,并非LL的第一个或最后一个节点都是虚拟记录。
请注意,您可以使用没有任何数据的虚拟节点和空指针作为显示LL中最后一个节点的标记。
你可能想知道有没有任何虚节点的LL是否可能? 答:是的。您可以保持LL的初始化,直到插入第一个数据条目,并且该点只有空指针作为LL,并且在插入之后保持指向头节点的指针并始终使用空指针作为“下一个” “尾节点的节点。
我建议您访问this页面以获取更多信息。
答案 1 :(得分:1)
是,答案是2.有时用作列表中的第一个和最后一个节点。
要回答这个问题,您需要了解虚拟节点的需求和使用。我将在链接列表问题的帮助下解释这一点。
假设您已经删除了单个链接列表中的节点,并且只有指向该节点的指针,如何删除? 答:如果我们有HEAD节点,我们可以简单地遍历,直到我们找到该节点并将其删除,但如果我们有最后一个节点的指针,这将不起作用,因为最后一个节点指向NULL。 这里我们需要DUMMY节点。这是一个空白节点,可以帮助我们以后建立删除节点的新节点。
在双重链接列表的情况下,此问题可以在任一方向。 虚拟节点的定义:列表前端/末尾的虚拟节点,仅用于减少链表操作中对特殊情况代码的需求。它是一个空模板,可以在以后构建新节点。 这里的问题是我们没有头节点。我们只有指向目标节点的指针。
解决方案将是这样的,我们将数据从下一个节点复制到节点删除和删除下一个节点的内容。
struct node *temp = node_ptr->next;
node_ptr->data = temp->data;
node_ptr->next = temp->next;
free(temp);
但如果我们有最后一个节点的指针,这将无法工作,因为最后一个节点指向NULL。 这里我们需要DUMMY节点。这是一个空白节点,可以帮助我们以后建立删除节点的新节点。
如果是双重链接列表,这个问题可以在任何一个方向。
虚拟节点的定义:列表前/末端的虚拟节点,仅用于减少链表操作中对特殊情况代码的需求。它是一个空模板,可以在以后构建新节点。
参考:http://pages.cs.wisc.edu/~vernon/cs367/notes/4.LINKED-LIST.html
答案 2 :(得分:0)
在算法问题中,我们总是将链表的头部作为参数传递。如果您正在更改头节点的位置并且需要返回新的头节点,那么问题将是您将如何返回新的头。这就是为什么我们最初创建一个虚拟节点并且 dummy.next
将指向头部。
Apple 面试问题之一是交换一对节点并以单向链表返回新头。
因为链表是一种方式,在我们交换了前 2 个节点之后(有问题你需要交换所有),我们将如何保持头节点的引用。这就是我们使用虚拟节点的地方。
dummy=new ListNode(dummyValue, head)
虚拟节点总是指向第一个节点,所以重新返回dummy.next
链表问题中有一个常见问题:从末尾删除第 n 个节点。
为了解决这个问题,我们初始化了慢指针和快指针。首先我们遍历快指针 n 次,所以当我们继续遍历快指针并到达链表末尾时,慢指针将落后 n 个节点。
然而,要从链表中删除一个节点,我们只需要剪切指向该节点的指针。如果没有指向该节点,它将被垃圾收集。
例如,如果我们有 5 个节点,我们需要从末尾删除第 2 个节点,则从末尾开始的第 3 个节点指向我们要删除的节点。所以我们实际上必须保留从末尾开始的第三个节点的引用,并将其 next
分配给最后一个节点。所以我们创建了一个虚拟节点,慢指针将从那里开始。在图像上显示会更容易:
如果第 n 个节点指向链表的头部,我们将返回 null。由于 dummy.next 是头部,我们将返回 dummy.next