1. 反转链表
//pre 指向前一个节点,cur 指向当前正在处理的节点,temp 暂存下一个节点ListNode* reverse(ListNode* head){ListNode* pre = nullptr, *cur = head, *temp;while(cur){temp = cur->next;cur->next = pre;pre = cur;cur = temp;}return pre;}
ListNode* reverse(ListNode* head){if (!head || !(head->next))return head;ListNode* newHead = reverse(head->next);head->next->next = head;head->next = nullptrreturn newHead;}
2. 判断链表中是否存在环
//快指针每次前进两个单位,慢指针每次前进一个单位,//如果链表中存在环则快慢指针一定会相遇 (尚不明白原理)bool hasCycle(ListNode *head) {ListNode* slow, *fast;slow = fast = head;//没有环时快指针到达链表末尾while(fast && fast->next){fast = fast->next->next;slow = slow->next;if (fast == slow) return true;}return false;}
//每次将当前节点的next指向自己,相当于从链表中删除自己,//如果最后遍历到了next指向自己的节点,则有两种可能://1. 链表中原本就存在next指向自己的节点,判断为有环//2. 该节点是处理过后才指向自己,则代表有后面的节点指向前面的节点,判断为有环bool hasCycle(ListNode *head) {ListNode* p = head, *next;// p == nullptr 时表示链表无环while(p){//判断是否有环,同时如果判断成功则 p 为环的入口if (p->next == p) return true;//从链表中删除当前节点next = p->next;p->next = p;p = next;}return false;}
3. 指出链表中环的起点
//前半部分就是上面判断是否存在环的代码//判断存在环后,将快指针移至链表头,将快慢指针同时后移一位直至相遇,//该节点则为环的入口ListNode* EntryNodeOfLoop(ListNode* pHead) {//快慢指针判断环,同上ListNode* fast = pHead, *slow = pHead;while(fast && fast->next){fast = fast->next->next;slow = slow->next;if (fast == slow) break;}//不存在环的情况,注意还要判断 fast->nextif (!fast || !(fast->next)) return nullptr;//寻找环的起点fast = pHead;while(fast != slow){fast = fast->next;slow = slow->next;}return fast;}
判断是否存在环中的逐个删除方法也可用来解此题,但实测效率不如快慢指针
