简体   繁体   English

链接列表中的头节点

[英]Head node in linked lists

I have problems with understanding what is the nature of the first node, or the so called head, in a linked list data structure. 我在理解链表数据结构中第一个节点或所谓的头部的性质时遇到了问题。 A linked list consists of nodes, and each node contains some data and a link to another node in the list. 链表由节点组成,每个节点包含一些数据和指向列表中另一个节点的链接。 But is the very first node a node which contains data and a link to the second node? 但是第一个节点是包含数据的节点还是到第二个节点的链接? Or is it contain only a link (and no data) to a node? 或者它只包含一个节点的链接(没有数据)? I thought that the very first node in a linked list has both data and a link to another node, but in one introductory book it is explained that the head is a node but a link that gets you to the first node. 我认为链表中的第一个节点既有数据又有到另一个节点的链接,但在一本介绍性书中,解释说head是一个节点,但是一个链接可以将你带到第一个节点。 At the same time head is a variable of the type of the node. 同时head是节点类型的变量。 Why is it like this? 为什么会这样? (I am working in Java, if that matters). (我在Java工作,如果这很重要)。 Thanks you. 谢谢。

These are called "dummy" header nodes, and they allow you to write general code that works for empty and non-empty lists. 这些被称为“虚拟”头节点,它们允许您编写适用于空列表和非空列表的通用代码。

Regularly, if you want to insert a Node at the end of your list, you need two cases. 通常,如果要在列表末尾插入Node ,则需要两种情况。 If head is null, indicating the list is empty, then you would set head to the new Node . 如果head为空,表明该列表是空的,那么你就设置head到新的Node If head is not null, then you follow the next pointers until you have the last Node , and set the next pointer to the new Node . 如果head不为null,则按照next指针直到有最后一个Node ,并设置指向新Nodenext指针。

However, if you use a dummy header, head will never be null. 但是,如果使用虚拟标头,则head永远不会为null。 It will be a Node with a null next pointer, which you can point to your new Node , just how you would if the list did contain nodes. 它将是一个带有空的next指针的Node ,您可以将其指向新Node ,如果列表确实包含节点,则指向您的节点。

A @falmarri answered, you can implement it either way. @falmarri回答说,你可以用任何一种方式实现它。 Head node is similar to any other node in a Singly Linked list. 头节点类似于单链接列表中的任何其他节点。 It is just a starting node with which we can traverse the rest of the linked list. 它只是一个起始节点,我们可以通过它来遍历链表的其余部分。 We can implement head as either a node or as a pointer. 我们可以将head实现为节点或指针。

Think of it like a Node is a object which has a variable "data" to hold the value and another variable "next" which points to another Node object to make a link. 可以把它想象成Node是一个对象,它有一个变量“data”来保存值,另一个变量“next”指向另一个Node对象来建立一个链接。 see the below java class. 看下面的java类。

public class ListNode {
private int data;
private ListNode next = null;

public ListNode() {
    // TODO Auto-generated constructor stub
}
//constructor for creating a listNode
public ListNode(int data){
    this.data = data;
}
/*below are setters and getters  */
public void setData(int data){
    this.data = data;
}
public int getData(){
    return this.data;
}
public void setNext(ListNode next){
    this.next = next;
}
public ListNode getNext(){
    return this.next;
}
}

and this is how i would link it. 这就是我如何链接它。

//create 3 list node objects
    ListNode one = new ListNode(1);
    ListNode two = new ListNode(2);
    ListNode three = new ListNode(3);

    one.setNext(two);
    two.setNext(three);

But note we need to know the head node for any further manipulation like adding a ListNode at end, beginning or at a random place in the List. 但请注意,我们需要知道头节点的任何进一步操作,例如在List的末尾,开头或随机位置添加ListNode。

a Head Node is one in our case from where the list chain has started. 在我们的案例中,Head Node是列表链开始的地方之一。

Hope it clears :) 希望它清除:)

Thanks Punith 谢谢Punith

You can implement it either way. 你可以用任何一种方式实现它。 A first node that has no data and just a link would be a pretty weird implementation though. 但是,没有数据而只是链接的第一个节点将是一个非常奇怪的实现。

A head node is normally like any other node except that it comes logically at the start of the list, and no other nodes point to it (unless you have a doubly-linked list). 头节点通常像任何其他节点一样,除了它在逻辑上位于列表的开头,并且没有其他节点指向它(除非你有一个双向链表)。

Since no other node points to it, and you also need an easy way to find the start of the list, it is common to store a separate pointer to a node that points to the head node. 由于没有其他节点指向它,并且您还需要一种简单的方法来查找列表的开头,因此通常会将一个单独的指针存储到指向头节点的节点。 This pointer is not a node-itself, just a pointer to one. 该指针不是节点本身,只是指向一个节点的指针。

If this was in C++, it might be easier for you to understand, but a header node is more just a reference that you use to gain the initial access to the entire list. 如果这是在C ++中,您可能更容易理解,但标题节点更多只是您用来获得对整个列表的初始访问权的引用。 It references the first "complete" node in the list which contains its data item within the list's data set and a reference to the next node. 它引用列表中的第一个“完整”节点,该节点包含列表数据集中的数据项和对下一个节点的引用。 If this was C++, a node would really be just a "pointer" to a data structure, which is just memory address for the compiler. 如果这是C ++,那么节点实际上只是数据结构的“指针”,它只是编译器的内存地址。 If you didn't have a header node that pointed to your linked-list, then it would be lost in the "ether" never to be accessed again - while still taking up space in memory. 如果你没有一个指向你的链表的标题节点,那么它将在“以太”中丢失,永远不会被再次访问 - 同时仍占用内存空间。

Since Java takes care of this for you behind the scenes, you don't actually have to worry about pointers. 由于Java在幕后为您处理这个问题,因此您实际上不必担心指针。 But, that could be the reason behind your confusion. 但是,这可能是你混淆的原因。 Since, so much detail is hidden, without any prior knowledge behind the concepts you would have to just accept the syntax rules without knowing the reasons behind them. 由于隐藏了如此多的细节,在没有任何先验知识背后的概念,您必须接受语法规则而不知道它们背后的原因。

In concept, arrays are a type of list, just like linked-lists are also a type of list. 在概念上,数组是一种列表,就像链表也是一种列表一样。 Arrays are placed in sequential order in memory whereas linked lists are not. 数组按顺序放在内存中,而链表则不是。 An array's member only references its data item but since the members are placed where they are in memory, you can just access them by adding an integer value multiplied by the size of that data item's data type to the reference for the entire array. 数组成员仅引用其数据项,但由于成员放在内存中,因此只需通过将整数值乘以该数据项的数据类型的大小添加到整个数组的引用即可访问它们。 This differs from linked-lists by the fact that linked lists aren't placed in sequential order and thus a more complex data structure must be used to make up the list - ie a "node". 这与链表不同,因为链表不是按顺序排列的,因此必须使用更复杂的数据结构来组成列表 - 即“节点”。

But, since the linked list isn't placed in any kind of order in memory, the compiler doesn't have to set aside a chunk of data for it and thus is why it can have any length you want it to without having to recreate a new one every time you change its length. 但是,由于链接列表没有以任何类型的顺序放在内存中,因此编译器不必为它预留一大块数据,这就是为什么它可以具有您想要的任何长度而无需重新创建每次更改长度时都要换一个新的。 This differs from an array since arrays' lengths are static. 这与数组不同,因为数组的长度是静态的。 Additionally, an array is referenced by its first member, that is (for an array named "a") this would be "a[0]" or the equivalent "a" if this were C. However, a linked list doesn't work like this and is why you have a "header" or "dummy" node to reference the entire thing. 另外,一个数组由它的第一个成员引用,即(对于一个名为“a”的数组),这将是“a [0]”或等效的“a”,如果这是C.但是,链接列表不是像这样工作,这就是为什么你有一个“标题”或“虚拟”节点来引用整个事物。

Another thing about the header node is that when performing various operations on a linked-list, you can also create a node that's similar in structure to your "head node" to help in performing your operation on the list. 关于标题节点的另一个问题是,当在链表上执行各种操作时,您还可以创建一个与“头节点”结构类似的节点,以帮助在列表上执行操作。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM