本系列作为本人刷LeeCode记录,主要记录思路,作为备忘,仅供参考。(啊,算法实在太难了。。。万里长征第一步,脑袋已经变糊涂)
文章目录
1、奇偶链表
将奇链表放在一个链表,偶链表放在另一个链表,最后把偶链表头结点接到奇链表尾结点。
class Solution {
public:
ListNode* oddEvenList(ListNode* head) {
if(head == NULL) return head;
ListNode* p = head;
ListNode* tmp = head -> next;
ListNode* cur = head -> next;
while(cur && cur -> next)
{
p -> next = cur -> next;
p = p -> next;
cur -> next = p -> next;
cur = cur -> next;
}
p -> next = tmp;
return head;
}
};
类似于拉链
2、相交链表
分别为链表A和链表B设置指针A和指针B,然后开始遍历链表,如果遍历完当前链表,则将指针指向另外一个链表的头部继续遍历,直至两个指针相遇。
class Solution {
public:
ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {
// A+B、B+A 长度相同,遍历,如果有交点,则同时同距离到达交点,
// 如果没有交点,则走完全长,返回NULL
if(headA == NULL || headB == NULL) return NULL;
ListNode* pA = headA;
ListNode* pB = headB;
// 第一轮是pA和pB第一次到达尾部的会移向另一链表的表头。
// 第二轮是如果相交,就返回交点,不相交最后就是NULL==NULL
while(pA != pB){
pA = pA == NULL ? headB : pA->next; // 如果pA为NULL,则pA=headB,否则为pA->next;
pB = pB == NULL ? headA : pB->next; // 如果pB为NULL,则pB=headA,否则为pB->next;
}
return pA;
}
};
3、删除链表的倒数第n个结点
思路一:先找到链表长度L,然后找到第L-n个结点,将第L-n+2个头结点接到L-n个尾结点。
class Solution {
public:
ListNode* removeNthFromEnd(ListNode* head, int n) {
if(head == NULL) return head;
// 为了确定链表长度,从而找到正数的第n个结点
int length = 0;
ListNode* dummpy = new ListNode(0);
dummpy->next = head;
ListNode* first = head;
while(first != NULL)
{
first = first->next;
length++;
}
// 将第L-n+2个结点接到第L-n个。即删掉L-n+1个结点,即导数第n个
length = length - n;
first = dummpy;
while(length > 0){
length--;
first = first->next;
}
first->next = first->next->next;
return dummpy->next;
}
};
思路二:双指针法,建立两个指针,fast和slow,fast先走,直到fast和slow间隔为n,然后两个指针同时走,直到fast==NULL。将slow的后一个结点接到slow前一个。(即删除倒数第n个结点)
class Solution {
public:
ListNode* removeNthFromEnd(ListNode* head, int n) {
// 定义快慢指针
ListNode *fast = head, *slow = head;
// 先让快指针走n步
while(fast){
if(n < 0) slow = slow->next;
n--;
fast = fast->next;
}
if(n == 0) return head->next;
slow->next = slow->next->next;
return head;
}
};