在学习链接列表的编码时,我遇到了这两件事,无法理解它们之间的区别,让我感到困惑。我从中学到的这本书在我们在链接列表末尾添加新节点的部分解释了“temp = * q”。
因此,如果列表不为空,即条件
指向列表中的第一个节点if(*q==NULL)
失败,那么下一部分将执行。现在temp
通过语句
temp=*q;
现在使用 temp ,我们使用statememnts遍历了整个链表:
while (temp->link!=NULL) temp=temp->link;
稍后在编码中,在列表的开头添加了一个新节点,我看到了:
现在我们需要使节点的
实现的link
部分指向现有的第一个节点。这是通过声明
temp->link=*q;
现在的问题是我无法区分这两个代码。他们不是在两种情境中扮演同样的角色吗?值得一提的是,temp
是一个临时节点,用于列表中的所有更新工作,*q
是起始节点。
答案 0 :(得分:4)
在开始使用temp
遍历第一个示例中的列表之前,您的内存布局如下:
然后创建一个局部变量temp
。让我们说最初它是空指针:
然后将temp
设为等于*q
:
temp=*q;
这使您的内存布局如下所示:
然后执行此循环:
while (temp->link!=NULL) temp=temp->link;
沿着列表的节点执行temp
,直到它指向最后一个节点。所以在我的示例图(有三个节点)中,temp
将首先移动到列表中的第二个节点:
然后它将移动到列表中的第三个节点:
循环结束于此,因为现在temp->link
为NULL
。
应该清楚的是,第一个赋值(temp=*q
)和循环中的赋值(temp=temp->link
)都不会改变链表的结构。这些赋值只会使temp
指向列表中的不同节点。
在第二个示例中,您将在列表的前面添加一个新节点。因此,您将temp
设置为指向新节点:
然后执行此语句,您发现令人困惑:
temp->link=*q;
以下是执行该语句后的内存布局:
应该很清楚,与第一个示例不同,temp
指向分配之前所做的分配之后的同一节点。
下一步(未在您的问题中显示)将更新*q
以指向新节点,并带有以下声明:
*q = temp;
这会将内存布局更改为:
现在您不再需要temp
了。大概你会从具有temp
的函数返回,它会消失,留下你的记忆:
答案 1 :(得分:1)
不,他们没有扮演同样的角色。
首先,要在开头和结尾插入的函数都将指针指向指向第一个节点,因此表示链表(指向头指针)的指针可以是相应更新。
在链接列表末尾插入时,首先temp = *q
使temp
指向列表中的第一个节点。 这里没有设置链接,这只是一个普通的指针复制。然后,你遍历到最后,并在最后插入一个新节点。
在前面插入时,首先为新节点分配空间,使temp
指向它,然后使 temp的链接指向列表的头部。这是通过temp->link = *q
完成的。 此处设置了一个链接。然后,头部本身已更改,因此*q = temp
。