leetcode刷题——数据结构(1):链表

链表

1. 找出两个链表的交点

第一次可做出,

解法可优化

2. 链表反转

递归/迭代 两种方法

3. 归并两个有序的链表

可做出

经典题型,两种方法需掌握

4. 从有序链表中删除重复节点

第一次可做出Ok

 

5. 删除链表的倒数第 n 个节点

第一次可做出Ok

 

6. 交换链表中的相邻结点

思考后可做出

解法可简化

7. 链表求和

第一次未做出

8. 回文链表

思考后可做出

解法可简化

9. 分隔链表

思考后可做出Ok

 

10. 链表元素按奇偶聚集

思考后可做出

 

链表是空节点,或者有一个值和一个指向下一个链表的指针,因此很多链表问题可以用递归来处理。

1. 找出两个链表的交点

160. Intersection of Two Linked Lists (Easy)

https://leetcode-cn.com/problems/intersection-of-two-linked-lists/

法一:
class Solution {
public:
    ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {
        ListNode *pa=headA,*pb=headB;
        while(pa!=NULL||pb!=NULL){
            if(pa==NULL) headB=headB->next;
            else pa=pa->next;
            if(pb==NULL) headA=headA->next;
            else pb=pb->next;
        }
        while(headA!=headB){
            headA=headA->next;
            headB=headB->next;
        }
        return headB;        
    }
};

法二:技巧性强
当访问 A 链表的指针访问到链表尾部时,令它从链表 B 的头部开始访问链表 B;同样地,当访问 B 链表的指针访问到链表尾部时,令它从链表 A 的头部开始访问链表 A。这样就能控制访问 A 和 B 两个链表的指针能同时访问到交点。
/**
 * 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 *pa=headA,*pb=headB;
        while(pa!=pb){
            pa=(pa==NULL)?headB:pa->next;
            pb=(pb==NULL)?headA:pb->next;
        }
        return pa;        
    }
};

2. 链表反转

206. Reverse Linked List (Easy)

https://leetcode-cn.com/problems/reverse-linked-list/

1.	递归
/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}
 * };
 */
class Solution {
public:
    ListNode* reverseList(ListNode* head) {
        if(head==NULL||head->next==NULL) return head;
        ListNode *hn=reverseList(head->next);
        head->next->next=head;
        head->next=NULL;
        return hn;
    }
};
2.	迭代
class Solution {
public:
    ListNode* reverseList(ListNode* head) {
        ListNode *ph=head,*res=NULL;
        while(ph!=NULL){
            ListNode* pn=ph->next;
            ph->next=res;
            res=ph;
            ph=pn;
        }
        return res;
    }
};

3. 归并两个有序的链表

21. Merge Two Sorted Lists (Easy)

https://leetcode-cn.com/problems/merge-two-sorted-lists/

1.	递归
class Solution {
public:
    ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
        if(l1==NULL||l2==NULL) return (l1==NULL)?l2:l1;
        if(l1->val<l2->val){
            l1->next=mergeTwoLists(l1->next,l2);
            return l1;
        }else{
            l2->next=mergeTwoLists(l1,l2->next);
            return l2;
        }
    }
};
2.	迭代
class Solution {
public:
    ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
        ListNode *l=new ListNode(-1),*pl=l;
        while(l1!=NULL&&l2!=NULL){
            if(l1->val<l2->val){
                pl->next=new ListNode(l1->val);
                l1=l1->next;
            }else{
                pl->next=new ListNode(l2->val);
                l2=l2->next;
            }
            pl=pl->next;
        }
        pl->next=(l1==NULL)?l2:l1;
        return l->next;
    }
};

4. 从有序链表中删除重复节点

83. Remove Duplicates from Sorted List (Easy)

https://leetcode-cn.com/problems/remove-duplicates-from-sorted-list/

5. 删除链表的倒数第 n 个节点

19. Remove Nth Node From End of List (Medium)

https://leetcode-cn.com/problems/remove-nth-node-from-end-of-list/

6. 交换链表中的相邻结点

24. Swap Nodes in Pairs (Medium)

https://leetcode-cn.com/problems/swap-nodes-in-pairs/

class Solution {
public:
    ListNode* swapPairs(ListNode* head) {
        ListNode *res=new ListNode(-1),*prev=res;
        res->next=head;
        while(prev->next!=NULL&&prev->next->next!=NULL){
            ListNode *pl=prev->next,*ph=prev->next->next;
            pl->next=ph->next;
            ph->next=pl;
            prev->next=ph;
            prev=pl;
        }
        return res->next;
    }
};

7. 链表求和

445. Add Two Numbers II (Medium)

https://leetcode-cn.com/problems/add-two-numbers-ii/

class Solution {
public:
    stack<int> buildStack(ListNode* l){
        stack<int> st;
        while(l!=NULL){
            st.push(l->val);
            l=l->next;
        }
        return st;
    }
    ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {
        stack<int> st1=buildStack(l1);
        stack<int> st2=buildStack(l2);
        ListNode* res=new ListNode(-1);
        int carry=0;
        while(!st1.empty()||!st2.empty()||carry){
            if(!st1.empty()){
                carry+=st1.top();
                st1.pop();
            }
            if(!st2.empty()){
                carry+=st2.top();
                st2.pop();
            }
            ListNode *pn=new ListNode(carry%10);
            pn->next=res->next;
            res->next=pn;
            carry/=10;
        }
        return res->next;        
    }
};

8. 回文链表

234. Palindrome Linked List (Easy)

https://leetcode-cn.com/problems/palindrome-linked-list/

题目要求:以 O(1) 的空间复杂度来求解。

切成两半,把后半段反转,然后比较两半是否相等。

class Solution {
public:
    ListNode* reverseList(ListNode* head){
        ListNode *rev=NULL;
        while(head!=NULL){
            ListNode *nt=head->next;
            head->next=rev;
            rev=head;
            head=nt;
        }
        return rev;
    }
    bool isPalindrome(ListNode* head) {
        ListNode *slow=head,*fast=head;
        while(fast!=NULL&&fast->next!=NULL){
            slow=slow->next;
            fast=fast->next->next;
        }
        ListNode *last=reverseList(slow);
        while(last!=NULL){
            if(head->val!=last->val) return false;
            head=head->next;
            last=last->next;
        }
        return true;
    }
};

9. 分隔链表

725. Split Linked List in Parts(Medium)

https://leetcode-cn.com/problems/split-linked-list-in-parts/

10. 链表元素按奇偶聚集

328. Odd Even Linked List (Medium)

https://leetcode-cn.com/problems/odd-even-linked-list/

class Solution {
public:
    ListNode* oddEvenList(ListNode* head) {
        if(head==NULL) return NULL;
        ListNode *odd=head,*even1=head->next,*even2=even1;
        while(even2!=NULL&&even2->next!=NULL){
            odd->next=even2->next;
            even2->next=even2->next->next;
            odd=odd->next;
            odd->next=even1;
            even2=even2->next;
        }
        return head;
    }
};

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值