• 代码随想录算法训练营第23期day4| 24. 两两交换链表中的节点 、19.删除链表的倒数第N个节点、面试题 02.07. 链表相交、142.环形链表II


    目录

    一、(leetcode 24)两两交换链表中的节点

    二、(leetcode 19)删除链表的倒数第N个节点

    思路

    三、(leetcode 160)链表相交

    四、(leetcode 142)环形链表II

    思路


    一、(leetcode 24)两两交换链表中的节点

    力扣题目链接

    状态:已AC,要设两个临时节点temp、temp1,不然指针指向错误,同时画图也很重要

    1. class Solution {
    2. public:
    3. ListNode* swapPairs(ListNode* head) {
    4. ListNode* dummyHead = new ListNode(0);
    5. dummyHead->next = head;
    6. ListNode* cur = dummyHead;
    7. while(cur->next!=NULL&&cur->next->next!=NULL)
    8. {
    9. ListNode*temp=cur->next;
    10. ListNode*temp1=cur->next->next->next;
    11. cur->next=cur->next->next;
    12. cur->next->next=temp;
    13. cur->next->next->next=temp1;
    14. cur=cur->next->next;
    15. }
    16. return dummyHead->next;
    17. }
    18. };

    二、(leetcode 19)删除链表的倒数第N个节点

    力扣题目链接

    状态:看完思路AC,注意fast指针走n+1步,以保证slow能走到想要的节点的前一个节点

    思路

    • 定义fast指针和slow指针,初始值为虚拟头结点

    • fast首先走n + 1步 ,这样同时移动slow的时候才能指向删除节点的上一个节点(方便做删除操作) 

    • fast和slow同时移动,直到fast指向末尾

    • 删除slow指向的下一个节点

    1. class Solution {
    2. public:
    3. ListNode* removeNthFromEnd(ListNode* head, int n) {
    4. ListNode* dummyHead = new ListNode(0);
    5. dummyHead->next = head;
    6. ListNode* slow = dummyHead;
    7. ListNode* fast = dummyHead;
    8. while(n-- && fast != NULL) {
    9. fast = fast->next;
    10. }
    11. fast = fast->next;
    12. while (fast != NULL) {
    13. fast = fast->next;
    14. slow = slow->next;
    15. }
    16. slow->next = slow->next->next;
    17. return dummyHead->next;
    18. }
    19. };

    三、(leetcode 160)链表相交

    力扣题目链接

    状态:已AC,注意不是数一样就行,而是指针一致

    1. class Solution {
    2. public:
    3. ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {
    4. ListNode* curA=headA;
    5. ListNode* curB=headB;
    6. int lenA=0,lenB=0;
    7. while(curA!=NULL)
    8. {
    9. lenA++;
    10. curA=curA->next;
    11. }
    12. while(curB!=NULL)
    13. {
    14. lenB++;
    15. curB=curB->next;
    16. }
    17. curA=headA;
    18. curB=headB;
    19. if (lenB > lenA) {// 让curA为最长链表的头,lenA为其长度
    20. swap (lenA, lenB);
    21. swap (curA, curB);
    22. }
    23. int gap=lenA-lenB;
    24. while(gap--)
    25. {
    26. curA=curA->next;
    27. }
    28. while(curA!=NULL)
    29. {
    30. if(curA==curB)
    31. {
    32. return curA;
    33. }
    34. curA=curA->next;
    35. curB=curB->next;
    36. }
    37. return NULL;
    38. }
    39. };

    四、(leetcode 142)环形链表II

    力扣题目链接

    状态:思路还需梳理,有一些数学推导容易考虑不到

    思路

    • 判断链表是否环
    • 如果有环,如何找到这个环的入口

    1)使用快慢指针法,分别定义 fast 和 slow 指针,从头结点出发,fast指针每次移动两个节点,slow指针每次移动一个节点,如果 fast 和 slow指针在途中相遇 ,说明这个链表有环

    2)判断环入口 

    2(x+y)=x+y+n(y+z)\Rightarrow x=(n-1)(y+z)+z

    p.s为什么slow指针是x+y,不是x+m(y+z)+y(如图)

    从头结点出发一个指针,从相遇节点 也出发一个指针,这两个指针每次只走一个节点, 那么当这两个指针相遇的时候就是 环形入口的节点

    1. class Solution {
    2. public:
    3. ListNode *detectCycle(ListNode *head) {
    4. ListNode* fast = head;
    5. ListNode* slow = head;
    6. while(fast != NULL && fast->next != NULL) {
    7. slow = slow->next;
    8. fast = fast->next->next;
    9. // 快慢指针相遇,此时从head 和 相遇点,同时查找直至相遇
    10. if (slow == fast) {
    11. ListNode* index1 = fast;
    12. ListNode* index2 = head;
    13. while (index1 != index2) {
    14. index1 = index1->next;
    15. index2 = index2->next;
    16. }
    17. return index2; // 返回环的入口
    18. }
    19. }
    20. return NULL;
    21. }
    22. };

     

  • 相关阅读:
    spring bean的作用域
    【第200篇原创文章】解决低于1%概率出现的芯片VPSS模块跑飞的问题
    编程开发中的的字符编码与解码-原理篇
    AI算力反碎片化:世界上最快的统一矩阵乘法
    Python 内置函数详解 (3) 进制转换
    redis的bitmap数据类型使用(亿级海量数据统计解决方案)
    机器学习:VC维的概念和用途
    vue将base64编码转为pdf方法
    房产政策松绑,VR看房助力市场回春
    题目 1067: 二级C语言-分段函数 sqrt、fabs、pow
  • 原文地址:https://blog.csdn.net/weixin_42179093/article/details/133244866