对于虚拟头结点的理解
设置虚拟头结点,可以避免对头结点的单独处理
以下是没有头结点的按值删除的代码:
//按值进行删除
ListNode* removeElements(ListNode* head, int val)
{
//删除头结点(将头结点向后移动一位即可)
while(head != NULL && head -> val = val){
ListNode* tmp = head;
head = head->next;
delete tmp;
}
//删除非头结点
ListNode* cur = head;
while(cur != NULL && cur -> next != NULL){
if(cur -> next -> val == val){
ListNode* tmp = cur -> next;
cur -> next = cur -> next -> next;
delete tmp;
}else{
cur = cur -> next;
}
}
return head;
}
以下是含虚拟头结点的按值删除的代码:
//按值进行删除
ListNode* removeElements(ListNode* head, int val)
{
//设置一个虚拟头结点
ListNode* dummyhead = new ListNode(0);
dummyhead -> next = head;
ListNode* cur = dummyhead;
while(cur != NULL && cur -> next != NULL){
if(cur -> next -> val == val){
ListNode* tmp = cur -> next;
cur -> next = cur -> next -> next;
delete tmp;
}else{
cur = cur -> next;
}
}
//设置虚拟头结点后,注意头结点变为了 dummyhead -> next
return dummyhead -> next;
}
力扣有关力扣经典例题
206.反转链表
class Solution {
public:
ListNode* reverseList(ListNode* head) {
if(head == NULL) return NULL;
ListNode* pre = head;
ListNode* cur = head->next;
while(cur != NULL)
{
// 保存一下 cur的下一个节点,因为接下来要改变cur->next
ListNode* temp = cur -> next;
cur -> next = pre;
pre = cur;
cur = temp;
}
head -> next = NULL;
return pre;
}
};
19.删除链表的倒数第N个节点
class Solution {
public:
ListNode* removeNthFromEnd(ListNode* head, int n) {
ListNode* dummyhead = new ListNode(0);
dummyhead -> next = head;
ListNode *slow = dummyhead;
ListNode *fast = dummyhead;
//fast指针先走n 步
while(n-- && fast != NULL){
fast = fast -> next;
}
//添加了虚拟头结点,为了让slow能指向待删除节点的前一个节点
fast = fast -> next;
while(fast != NULL){
slow = slow -> next;
fast = fast -> next;
}
//删除链表的倒数第 N 个结点
slow -> next = slow -> next -> next;
return dummyhead -> next;
}
};
142.环形链表 II
class Solution {
public:
ListNode *detectCycle(ListNode *head) {
ListNode* fast = head;
ListNode* slow = head;
while(fast != NULL && fast -> next != NULL){
fast = fast -> next -> next;
slow = slow -> next;
if(slow == fast){
slow = head;//一个从head开始走
fast = fast;//一个从第一次相遇点开始走
while(slow != fast){
slow = slow -> next;
fast = fast -> next;
}
return slow;
}
}
return NULL;
}
};
24.两两交换链表中的节点
//非递归写法
class Solution {
public:
ListNode* swapPairs(ListNode* head) {
//带虚拟头结点
ListNode* dummyhead = new ListNode(0);
dummyhead -> next = head;
ListNode *cur = dummyhead;
while(cur -> next != NULL && cur -> next -> next != NULL){
ListNode *tmp = cur -> next;
ListNode *tmp1 = cur -> next -> next -> next;
cur -> next = cur -> next -> next;
cur -> next -> next = tmp;
cur -> next -> next -> next = tmp1;
// cur移动两位,准备下一轮交换
cur = cur -> next -> next;
}
return dummyhead -> next;
}
};
链表相交
class Solution {
public:
ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {
ListNode *A = headA;
ListNode *B = headB;
while(A != B){
A = (A != NULL) ? A -> next : headB;
B = (B != NULL) ? B -> next : headA;
}
return A;
}
};