ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

LeetCode:合并k个有序的链表

2021-02-28 18:30:12  阅读:156  来源: 互联网

标签:ListNode int list lists next 链表 有序 return LeetCode


You are given an array of k linked-lists,each linked-list is sorted in ascending order.
Merge all the linked-lists into one sorted linked-list and return it.

Example 1:
Input: lists = [[1,4,5],[1,3,4],[2,6]]
Output: [1,1,2,3,4,4,5,6]
Explanation: The linked-lists are:
[
  1->4->5,
  1->3->4,
  2->6
]
merging them into one sorted list:
1->1->2->3->4->4->5->6

Example 2:
Input: lists = []
Output: []

Example 3:
Input: lists = [[]]
Output: []
 
题目大意:
给定k个增序的链表,试将它们合并成一条增序链表.

解题思路:
方法1:
枚举数组中所有链表的元素,存储在一个数组中,然后进行排序,即可.时间复杂度为O(n),空间复杂度也为O(n).

方法2:
分治思想,先每次拆分成k/2.最终再进行合并.

方法3:
优先队列.把所有的链表存储在一个优先队列中,每次提取所有链表头部节点值最小的那个节点,直到所有链表都被提取完.
需要设置一个比较类Comp,实现最小堆.因此operate()中返回时用大于号而不是等增关系的小于号进行比较.
#include <iostream>
#include <vector>
#include <algorithm>
#include <queue>

using namespace std;

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:
     Solution(){
         root=new ListNode(0);//利用指针,在堆上开辟空间,不能用栈上的局部变量返回地址.
         tmp=nullptr;
     }
     ListNode* mergeKLists(vector<ListNode*>& lists){
         if(lists.empty()) return nullptr;
         vector<int> res;
         for(auto& list:lists){
             while(list){
                 res.push_back(list->val);
                 list=list->next;
             }
         }
         sort(res.begin(),res.end()); 

         ListNode* head=root; 
         for(int i=0;i<res.size();i++){ 
             tmp=new ListNode(res[i]);  
             head->next=tmp;
             head=tmp;
         }  
         return root->next;//调试了很久,返回的根节点不存储值才行
     }

private:
     ListNode* root; 
     ListNode* tmp;
};

//方法二:归并排序
class SolutionOne{
public:
    ListNode* mergeKLists(vector<ListNode*>& lists){
        return merge(lists,0,lists.size()-1);
    }
    ListNode* merge(vector<ListNode*>& lists,int l,int r){
        if(l==r) return lists[l];
        if(l>r) return nullptr;
        int mid=(l+r)>>1;
        return MergeTwoLists(merge(lists,l,mid),merge(lists,mid+1,r));
    }

    ListNode* MergeTwoLists(ListNode* l,ListNode* r){
        if(l==nullptr||r==nullptr)
           return l?l:r;
        ListNode head,*tail=&head;
        ListNode *pre1=l,*pre2=r;
        while(pre1&&pre2){
            if(pre1->val<=pre2->val){
                tail->next=pre1;
                pre1=pre1->next;
            }else{
                tail->next=pre2;
                pre2=pre2->next;
            }
            tail=tail->next;
        }
        tail->next=(pre1?pre1:pre2);
        return head.next;
    }
};

//方法三:优先队列
class SolutionTwo{
public:
    ListNode* MergeKLists(vector<ListNode*>& lists){
        if(lists.empty()) return nullptr;
        //priority_queue默认三个参数
        //Type就是数据类型,Container就是容器类型(Container必须是用数组实现的容器,
        //比如vector,deque等等,但不能用 list.STL里面默认用的是vector),Functional 就是比较的方式。
        priority_queue<ListNode*,vector<ListNode*>,Comp> q;
        for(ListNode* list:lists){
            if(list){
                q.push(list);
            }
        }
        ListNode root;
        ListNode* dummy=&root,*cur=dummy;
        while(!q.empty()){
            cur->next=q.top();
            q.pop();
            cur=cur->next;
            if(cur->next){
                q.push(cur->next);
            }
        }
        return root.next;
    }

    struct Comp{
        bool operator()(ListNode* l1,ListNode* l2){
            return l1->val>l2->val; //最小堆
        }
    };
};
int main(int argc,char* argv[]){

    return 0;
}

 

标签:ListNode,int,list,lists,next,链表,有序,return,LeetCode
来源: https://blog.csdn.net/Jiangtagong/article/details/114234729

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有