[4]-代码随想录算法训练营-day4-链表-part2
代码随想录算法训练营第四天|链表-part2
1.Leecode 24.两两交换链表中的节点
题目
- https://leetcode.cn/problems/swap-nodes-in-pairs/
思路
- 虚拟头节点
tmp
变量记录- 交换
刷随想录后想法
tmp
变量需要两个实现困难
- 交换后链表连接逻辑存在错漏
实现代码
/** * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode() : val(0), next(nullptr) {} * ListNode(int x) : val(x), next(nullptr) {} * ListNode(int x, ListNode *next) : val(x), next(next) {} * }; */ class Solution { public: ListNode* swapPairs(ListNode* head) { ListNode* dummyHead = new ListNode(0); //虚拟头节点 dummyHead->next = head; ListNode* cur = dummyHead; ListNode *tmp, *tmp1; while(cur && cur->next && cur->next->next){ tmp = cur->next; tmp1= cur->next->next->next; cur->next = tmp->next; tmp->next->next = tmp; tmp->next = tmp1; cur =cur->next->next; } return dummyHead->next; } };
学习收获
- 善用
dummyHead
- 编程前,画图计算,逻辑演算,避免存在逻辑错漏
2.LeetCode 19.删除链表倒数第N个节点
题目
- https://leetcode.cn/problems/remove-nth-node-from-end-of-list/
思路
- 思路1:暴力,先获取size,再次确定要删除的节点
- 思路2:栈
- 思路3:递归
刷随想录想法
- 双指针
- 快指针
fast
先移动n+1步- 慢指针
slow
,随后同步移动slow
指向了待删除节点的前一个节点,执行删除操作即可实现困难
while
循环中,关于fast
和slow
快多少步的问题,老报地址越界问题实现代码
/** * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode() : val(0), next(nullptr) {} * ListNode(int x) : val(x), next(nullptr) {} * ListNode(int x, ListNode *next) : val(x), next(next) {} * }; */ class Solution { public: ListNode* removeNthFromEnd(ListNode* head, int n) { ListNode *dummyHead = new ListNode(0); dummyHead->next = head; ListNode *slow = dummyHead; ListNode *fast = dummyHead; while(n-- && fast){ fast = fast->next; } fast = fast->next; while(fast){ fast = fast->next; slow = slow->next; } ListNode *tmp = slow->next; slow->next = tmp->next; delete tmp; return dummyHead->next; } };
学习收获
- 关于
while(n--)
,先判断n是否为0,再进行减减操作,若n=2
,则while
循环两次。while(n--){ //..... } //等价于 while(n){ n--; //..... }
n--
与--n
,运算符在前则先运算,反之则先判断在运算。
3.LeetCode 面试题02.07.链表相交
题目
- https://leetcode.cn/problems/intersection-of-two-linked-lists-lcci/
思路
- 暴力,两层while循环
刷随想录想法
- 求长度,位置对齐后比较
实现困难
int lenA, lenB = 0;
这里lenA
居然没有被初始化为0,然后导致一致过不了样例!!!实现代码
/** * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode(int x) : val(x), next(NULL) {} * }; */ class Solution { public: ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) { ListNode *curA = headA; ListNode *curB = headB; int lenA = 0; int lenB = 0; int count = 0; while(curA){ curA = curA->next; lenA++; } while(curB){ curB = curB->next; lenB++; } //这里一定要先执行cur = head操作 if(lenA < lenB){ //lenA > lenB, 交换,让curA表示长的 curA = headB; curB = headA; count = lenB - lenA; }else{ curA = headA; curB = headB; count = lenA - lenB; } while(curA && count--){ curA = curA->next; } //现在A和B尾部对齐了 while(curA && curB && curA != curB){ curA = curA->next; curB = curB->next; } return curA; } };
4.LeetCode 142.环形链表
题目
- https://leetcode.cn/problems/linked-list-cycle-ii/
思路
- 无
刷随想录想法
- 感觉偏向数学问题了
实现困难
- 首先是对数学问题的分析
- 其次是将数学问题编程化
- 最后,对整个过程还有一点模糊
实现代码
/** * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode(int x) : val(x), next(NULL) {} * }; */ class Solution { public: ListNode *detectCycle(ListNode *head) { ListNode *fast = head; ListNode *slow = head; while(fast && fast->next){ fast = fast->next->next; slow = slow->next; if(fast == slow){ ListNode *index1 = fast; ListNode *index2 = head; while(index1 != index2){ index1 = index1->next; index2 = index2->next; } return index1; } } return NULL; } };