public void addLast(int data){
/*尾插法,突破点在于找到最后一个节点*/
ListNode node=new ListNode(data);//new出新的节点
ListNode cur=head;
//cur-头节点的“替身”,链表头节点不断发生变化不太合适
while(cur!=null){
cur=cur.next;//去往下一节点
}
/*循环结束,此时cur已经到了最后一个节点位置*/
cur.next=node;//cur指向尾插节点
}
上述 addLast
方法中,存在一个关键的逻辑错误,这会导致在尝试将新节点添加到链表末尾时发生 NullPointerException
。问题在于,当 cur
遍历到链表的最后一个节点时,cur
会变成 null
,因为最后一个节点的 next
是 null
。在 while
循环结束后,尝试访问 cur.next
,但此时 cur
已经是 null
,因此会导致空指针异常。
正确的实现应该是这样的:
public void addLast(int data){
/*尾插法,突破点在于找到最后一个节点*/
ListNode node=new ListNode(data);//new出新的节点
ListNode cur=head;
//cur-头节点的“替身”,链表头节点不断发生变化不太合适
while(cur.next!=null){
cur=cur.next;//去往下一节点
}
/*循环结束,此时cur已经到了最后一个节点位置*/
cur.next=node;//cur指向尾插节点
}
关键点在于
while(cur.next!=null) !!
代码解释:
-
创建新节点:首先,使用传入的
data
创建一个新的ListNode
节点。 -
检查链表是否为空:如果链表当前为空(即
head
为null
),则直接将新节点设置为头节点,并结束方法。 -
遍历链表:使用一个循环遍历链表,直到找到最后一个节点(即
cur.next
为null
的节点)。在循环中,cur
不断通过cur.next
前进到下一个节点。 -
添加新节点:当循环结束时,
cur
将指向链表的最后一个节点。此时,将新节点的引用赋给cur.next
,从而将新节点添加到链表的末尾。
这样修改后的方法就能正确地处理链表的尾插操作,无论是链表为空还是链表已包含多个节点的情况。