目录

  • 链表
    • 标记简介
      • 移除链表元素
        • 203.移除链表元素(√)
        • 237. 删除链表中的节点(√)
        • 83. 删除排序链表中的重复元素(√)
        • 82. 删除排序链表中的重复元素 II
      • 追赶指针技巧(双指针/快慢指针)
        • 876. 链表的中间结点(√)
        • 剑指 Offer 22. 链表中倒数第k个节点(√)
        • 141. 环形链表(√)
        • 142. 环形链表 II / 剑指 Offer II 022. 链表中环的入口节点(√)
        • 160. 相交链表(√)
        • 61. 旋转链表(√)
      • 反转链表
        • 206. 反转链表(√)
        • 92. 反转链表 II(√)
        • 24. 两两交换链表中的节点(√)
        • 面试题 02.05. 链表求和
        • 88. 合并两个有序数组(√)
        • 21. 合并两个有序链表(√)
        • 23. 合并K个升序链表(hard)(√)
        • 148. 排序链表
        • 138. 复制带随机指针的链表

链表

标记简介

一个(×)代表看不懂题解。
没有标记代表没有整理。
一个(√)代表能看懂解析和代码,有思路,实现不完全。
两个(√)代表有思路,能自己实现。
三个(√)代表掌握,从思路-》代码实现-》时间、空间复杂度。
四个(√)代表完全掌握,从思路-》代码实现-》时间、空间复杂度-》不同解法-》相似题型。

移除链表元素

203.移除链表元素(√)

/*** 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* removeElements(ListNode* head, int val) {if(head == nullptr) return nullptr;ListNode* dummy = new ListNode(0);dummy->next = head;ListNode* p = dummy;while(p->next != nullptr){if(p->next->val == val){ListNode* tmp = p->next;p->next = p->next->next;delete tmp;}else{p = p->next;}}return dummy->next;}
};

237. 删除链表中的节点(√)

请编写一个函数,使其可以删除某个链表中给定的(非末尾)节点。传入函数的唯一参数为 要被删除的节点 。

偷梁换柱

class Solution {public:void deleteNode(ListNode* node) {if(node == NULL) { return; }node->val = node->next->val;node->next = node->next->next;}
};

83. 删除排序链表中的重复元素(√)

链接: 83.删除排序链表中的重复元素.

class Solution {public:ListNode* deleteDuplicates(ListNode* head) {if(head == nullptr) { return nullptr; }ListNode* node = head;while(node->next != nullptr){if(node->val == node->next->val){ListNode* temp = node->next;node->next = temp->next;delete temp;}else{node = node->next;}}return head;}
};

82. 删除排序链表中的重复元素 II

链接: 82.删除排序链表中的重复元素 II.

class Solution {public:ListNode* deleteDuplicates(ListNode* head) {if(head == nullptr){return nullptr;}ListNode* dummy = new ListNode(0);dummy->next = head;ListNode* node = dummy;while(node->next != nullptr && node->next->next != nullptr){if(node->next->val == node->next->next->val){int val_prev = node->next->val;while(node->next != nullptr && val_prev == node->next->val){ListNode* temp = node->next;node->next = temp->next;delete temp;}}else{node = node->next;}}return dummy->next;}
};
  1. 分隔链表
    链接: 83. 分隔链表.
class Solution {public:ListNode* partition(ListNode* head, int x) {if(head == nullptr){return nullptr;}ListNode* leftDummy = new ListNode(0);ListNode* left = leftDummy;ListNode* rightDummy = new ListNode(0);ListNode* right = rightDummy;ListNode* node = head;while(node != nullptr){if(node->val < x){left->next = node;left = left->next;}else{right->next = node;right = right->next;}node = node->next;}right->next = nullptr;left->next = rightDummy->next;return leftDummy->next;}
};

追赶指针技巧(双指针/快慢指针)

对于寻找list某个特定位置的问题,不妨⽤两个变量chaser与runner,以不同的速度遍历list,找到⽬标位置: ListNode *chaser = head, *runner = head。

876. 链表的中间结点(√)

链接: 876. 链表的中间结点.

class Solution {public:ListNode* middleNode(ListNode* head) {if(head == nullptr) { return nullptr; }ListNode* slow = head;ListNode* fast = head;while(fast != nullptr && fast->next != nullptr){slow = slow->next;fast = fast->next->next;}return slow;}
};

剑指 Offer 22. 链表中倒数第k个节点(√)

链接: 链表中倒数第k个节点.

class Solution {public:ListNode* dummy = new ListNode(0);dummy->next = head;ListNode* fast = dummy;ListNode* slow = dummy;while(fast->next && k--){fast = fast->next;}while(fast->next != nullptr){fast = fast->next;slow = slow->next;}return slow->next->val;}
};
class Solution {public:ListNode* removeNthFromEnd(ListNode* head, int n) {if(head == nullptr || n < 0) { return nullptr; }ListNode* dummy = new ListNode(0);dummy->next = head;ListNode* fast = dummy;ListNode* slow = dummy;while(fast->next && n--){fast = fast->next;}while(fast->next != nullptr){fast = fast->next;slow = slow->next;}ListNode* tmp = slow->next;slow->next = slow->next->next;delete tmp;return dummy->next;}
};

141. 环形链表(√)

链接: 141. 环形链表.

class Solution {public:bool hasCycle(ListNode *head) {if ((head == nullptr) || (head->next == nullptr))  return false;ListNode *slow = head;ListNode *fast = head;do{if((fast == nullptr) || (fast->next == nullptr))  {return false;}slow = slow->next;fast = fast->next->next;}while(slow != fast);return true;}
};
class Solution {public:bool hasCycle(ListNode *head) {if(head == NULL) { return false; }ListNode* fast = head;ListNode* slow = head;while(fast && fast->next){fast = fast->next->next;slow = slow->next;if(fast == slow) { return true; }}return false;}
};

142. 环形链表 II / 剑指 Offer II 022. 链表中环的入口节点(√)

链接: 142. 环形链表 II.

class Solution {public:ListNode *detectCycle(ListNode *head) {if(head == NULL){return NULL;}ListNode* slow = head;ListNode* fast = head;do{if((fast == NULL) || (fast->next == NULL)){return NULL;}slow = slow->next;fast = fast->next->next;}while(slow != fast);ListNode* ptr = head;while(slow != ptr){ptr = ptr->next;slow = slow->next;}return slow;}
};
class Solution {public:bool hasCycle(ListNode *head) {if(head == NULL) { return false; }ListNode* fast = head;ListNode* slow = head;while(fast && fast->next){fast = fast->next->next;slow = slow->next;if(fast == slow) { return true; }}return false;}
};

160. 相交链表(√)

链接: 160.相交链表.

class Solution {public:ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {ListNode* curA = headA;ListNode* curB = headB;int lenA = 0;int lenB = 0;while(curA != NULL){lenA++;curA = curA->next;}while(curB != NULL){lenB++;curB = curB->next;}curA = headA;curB = headB;if(lenB > lenA){swap(lenA, lenB);swap(curA, curB);}int gap = lenA - lenB;while(gap--) { curA = curA->next; }while(curA != NULL){if(curA == curB) { return curA; }curA = curA->next;curB = curB->next;}return NULL;}
};

61. 旋转链表(√)

链接: 61. 旋转链表.

class Solution {public:ListNode* rotateRight(ListNode* head, int k) {if(head == nullptr || head->next == nullptr || k == 0){return head;}int count = 1;ListNode* p = head;while(p->next != nullptr){p = p->next;count++;}int offset = count - k % count;if(offset == count){return head;}p->next = head;while(offset--){p = p->next;}ListNode* ret = p->next;p->next = nullptr;return ret;}
};

反转链表

206. 反转链表(√)

链接: 206. 反转链表.

class Solution {public:ListNode* reverseList(ListNode* head) {ListNode* pre = nullptr;ListNode* cur = head;ListNode* tmp;while (cur) {tmp = cur->next;cur->next = pre;pre = cur;cur = tmp;}return pre;}
};

92. 反转链表 II(√)

给你单链表的头指针 head 和两个整数 left 和 right ,其中 left <= right 。请你反转从位置 left 到位置 right 的链表节点,返回 反转后的链表 。

class Solution {public:ListNode* reverseBetween(ListNode* head, int left, int right) {// 设置 dummyNode 是这一类问题的一般做法ListNode *dummy = new ListNode(0);dummy->next = head;ListNode *pre = dummy;for (int i = 0; i < left - 1; i++) {pre = pre->next;}ListNode *cur = pre->next;ListNode *tmp;for (int i = 0; i < right - left; i++) {tmp = cur->next;cur->next = tmp->next;tmp->next = pre->next;pre->next = tmp;}return dummy->next;}
};

24. 两两交换链表中的节点(√)

链接: 24. 两两交换链表中的节点.

class Solution {public:ListNode* swapPairs(ListNode* head) {if(head == nullptr) { return nullptr; }ListNode* dummy = new ListNode(0);dummy->next = head;ListNode* prev = dummy;ListNode* node1 = head, *node2 = head->next;while(node1 && node1->next){node2 = node1->next;//swap the "next" of prev nodesprev->next = node1->next;  // = node2//swap the "next" of current nodesnode1->next = node2->next;node2->next = node1;prev = node1;node1 = prev->next;}return dummy->next;}
};

这个版本好理解。

class Solution {public:ListNode* swapPairs(ListNode* head) {ListNode* dummy = new ListNode(0);dummy->next = head;ListNode* cur = dummy;ListNode* tmp1;ListNode* tmp2;while(cur->next != nullptr && cur->next->next != nullptr){tmp1 = cur->next;tmp2 = cur->next->next;cur->next = tmp2;tmp1->next = tmp2->next;tmp2->next = tmp1;cur = tmp1;}return dummy->next;}
};
class Solution {public:ListNode* swapPairs(ListNode* head) {if(head == nullptr) { return nullptr; }ListNode* dummy = new ListNode(0);dummy->next = head;ListNode* cur = dummy;while((cur->next != nullptr) && (cur->next->next != nullptr)){ListNode* tmp1 = cur->next;ListNode* tmp2 = cur->next->next->next;cur->next = cur->next->next;cur->next->next = tmp1;tmp1->next = tmp2;cur = cur->next->next;}return dummy->next;}
};

面试题 02.05. 链表求和

链接: 面试题 02.05. 链表求和.

class Solution {public:ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {ListNode dummy(0);ListNode* p = &dummy;int cn = 0;while(l1 || l2){int val = cn + (l1 ? l1->val : 0) + (l2 ? l2->val : 0);cn = val / 10;val = val % 10;p->next = new ListNode(val);p = p->next;if(l1){l1 = l1->next;}if(l2){l2 = l2->next;}}if(cn != 0){p->next = new ListNode(cn);p = p->next;}return dummy.next;}
};

88. 合并两个有序数组(√)

class Solution {public:void merge(vector<int>& nums1, int m, vector<int>& nums2, int n) {int p1 = m - 1, p2 = n - 1, cur = m + n - 1;while(p1 >= 0 && p2 >= 0){nums1[cur--] = nums1[p1] > nums2[p2] ? nums1[p1--] : nums2[p2--];}while(p2 >= 0){nums1[cur--] = nums2[p2--];}}
};

21. 合并两个有序链表(√)

链接: 21. 合并两个有序链表.

class Solution {public:ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {ListNode* dummy = new ListNode(0);ListNode* cur = dummy;while(l1 && l2){if(l1->val <= l2->val){cur->next = l1;l1 = l1->next;}else{cur->next = l2;l2 = l2->next;}cur = cur->next;}cur->next = (l1 != nullptr) ? l1 : l2;return dummy->next;}
};

23. 合并K个升序链表(hard)(√)

链接: 23. 合并K个升序链表.

/*** 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 {private:ListNode* mergeTwoLists(ListNode* l1, ListNode* l2){ListNode* dummy = new ListNode(0);ListNode* cur = dummy;while(l1 && l2){if(l1->val <= l2->val){cur->next = l1;l1 = l1->next;}else{cur->next = l2;l2 = l2->next;}cur = cur->next;}cur->next = (l1 != nullptr) ? l1 : l2;return dummy->next; }
public:ListNode* mergeKLists(vector<ListNode*>& lists) {if(lists.empty()) return nullptr;ListNode* p = lists[0];for(int i=1; i<lists.size(); ++i){p = mergeTwoLists(p, lists[i]);}return p;}
};

148. 排序链表

/*** 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* sortList(ListNode* head) {if(head == nullptr || head->next == nullptr) return head;ListNode* head1 = head;ListNode* head2 = split(head);head1 = sortList(head1);head2 = sortList(head2);return merge(head1, head2);}ListNode* split(ListNode* node){ListNode* slow = node;ListNode* fast = node->next;while(fast && fast->next){slow = slow->next;fast = fast->next->next;}ListNode* splitHead = slow->next;slow->next = nullptr;return splitHead;}ListNode* merge(ListNode* node1, ListNode* node2){ListNode* p1 = node1;ListNode* p2 = node2;ListNode* dummy = new ListNode(0);ListNode* p = dummy;while(p1 && p2){if(p1->val < p2->val){p->next = p1;p1 = p1->next;}else{p->next = p2;p2 = p2->next;}p = p->next;}p->next = (p1 == nullptr) ? p2 : p1;return dummy->next;}
};

138. 复制带随机指针的链表

链接: 138. 复制带随机指针的链表.

刷题笔记(1)---链表相关推荐

  1. LeetCode Java刷题笔记—876. 链表的中间结点

    876. 链表的中间结点 给定一个头结点为 head 的非空单链表,返回链表的中间结点.如果有两个中间结点,则返回第二个中间结点. 简单难度.使用快慢指针即可,快指针fast每次走2步,慢指针slow ...

  2. java二叉树转换为链表_leetcode刷题笔记-114. 二叉树展开为链表(java实现)

    leetcode刷题笔记-114. 二叉树展开为链表(java实现) 题目描述 给你二叉树的根结点 root ,请你将它展开为一个单链表: 展开后的单链表应该同样使用 TreeNode ,其中 rig ...

  3. 赞!Google 资深软件工程师 LeetCode 刷题笔记首次公开

    有人说写代码就像我们平时开车,仅凭经验你就可以将车开走:但当有一天,这辆车出问题跑不起来的时候,你不懂汽车的运行机制,你要怎么排除和解决问题?所以拥有扎实的数据结构和算法,才能开好编程这辆车. 作为程 ...

  4. Google 资深软件工程师 LeetCode 刷题笔记首次公开

    BAT 等国内的一线名企,在招聘工程师的过程中,对算法和数据结构都会重点考察.但算法易学难精,我的很多粉丝技术能力不错,但面试时总败在算法这一关,拿不到好 Offer.但说实话,数据结构和算法花点时间 ...

  5. 《编程能力基础》刷题笔记(41 题)

    <编程能力基础>刷题笔记 1. 单调数列 题解:递归.模拟.API 2. 实现 strStr() 题解:API.暴力.滑动窗口 3. 平衡二叉树 题解:迭代 4. 重复的子字符串 题解:模 ...

  6. LeetCode《编程能力入门》刷题笔记(34 题全)

    LeetCode<编程能力入门>刷题笔记 基本数据类型 1. 在区间范围内统计奇数数目 _解法1:暴力迭代 _解法2:数学(找规律) 2. 去掉最低工资和最高工资后的工资平均值 _解法1: ...

  7. 《剑指 Offer I》刷题笔记 20 ~ 30 题

    <剑指 Offer I>刷题笔记 20_30 动态规划(简单) 20. 斐波那契数列 _解法1:迭代 解法2:记忆化递归 解法3:动态规划 21. 青蛙跳台阶问题 _解法1:动态规划 22 ...

  8. 《剑指 Offer I》刷题笔记 1 ~10 题

    <剑指 Offer I>刷题笔记 1 ~10 题 栈与队列(简单) 1. 用两个栈实现队列 _解法 1:暴力做法 解法 2:优化解法 1 2. 包含 min 函数的栈 _解法 1:pop( ...

  9. 《剑指Offer》力扣刷题笔记(03-10)

    <剑指Offer>力扣刷题笔记(03-10) 最近确实有点闲,想在进组搬砖之前找点有意义的事干,于是,就开始刷<剑指Offer>.<程序员面试金典>等书上的题目,也 ...

  10. 操作系统,计算机网络,数据库刷题笔记11

    操作系统,计算机网络,数据库刷题笔记11 2022找工作是学历.能力和运气的超强结合体,遇到寒冬,大厂不招人,可能很多算法学生都得去找开发,测开 测开的话,你就得学数据库,sql,oracle,尤其s ...

最新文章

  1. Python_python内置函数
  2. 基于ASP.NET的新闻管理系统(三)代码展示
  3. for循环python爬虫_python爬虫 for循环只出来一条
  4. Struts2第九篇【OGNL、valueStack详解】
  5. java怎样实现重载一个方法
  6. VS2010安装VC9 RunTime 失败的问题
  7. Linux ALSA声卡驱动之二:声卡的创建
  8. C++ 回调函数简单示例
  9. 便携式明渠流量计的功能特点及资质证书
  10. Mean Rank 和Mean reciprocal rank
  11. Redis缓存问题总结
  12. 大数据和云计算技术周报(第102期)
  13. paste shell 分隔符_Shell paste命令
  14. Android开发12年高级工程师:作为 IT 行业的过来人,我想对你们说~(职场必看!!!)
  15. pb9 日历控件(源码)
  16. mac python2.7升级到3.7_Mac下python2.7 升级到3.7
  17. 求素数(质数)的方法
  18. PyQt5+fitz实现图片与PDF互相转换
  19. 开源的业务中台 全渠道一盘货 订单管理系统 OMS
  20. 计算机毕业设计Node.js+Vue基于的宠物领养管理系统(程序+源码+LW+部署)

热门文章

  1. 照片纸特效多画面滚动动画展示PR视频剪辑模板
  2. Android音视频【三】硬解码播放H264
  3. C语言中 .h文件和.c文件的区别 (转)
  4. ES7、ES8、ES9、ES10、ES11 新特性 总结
  5. 公众号自动回复不生效php,php,微信公众平台开发者_微信公众号开发者自动回复设置没反应,php,微信公众平台开发者 - phpStudy...
  6. 『牛角书』基于JS实现的鸿蒙游戏——二十四点纸牌
  7. Java Servlet 详解:(三)在 IDES 中开发 Servlet-多图警告
  8. C语言 输入一个数值,分析是正还是负,并打印出此数
  9. 【软件监控神器】Procmon
  10. iOS_实现类似蒲公英、fir等发包平台 通过URL分发内测APP