您的位置:首页 > 职场人生

剑指Offer_面试题17_合并两个有序链表

2017-07-27 12:36 507 查看


题目描述

输入两个单调递增的链表,输出两个链表合成后的链表,当然我们需要合成后的链表满足单调不减规则。
分析:这道题有点类似于面试题4_替换空格中的扩展题目:两个有序数组合并。大体思路上是一致的,代码很类似,分别遍历两个链表,将小的结点链接到新链表表尾。后期处理有点区别就是,合并数组在循环结束后,需要用while把剩余的一个数组中的元素一次加入新数组。而本题只需要用if判断哪个链表不空然后把剩下的直接链接到新链表即可,这是链表不同于顺序表的地方,存储方式不同。

/*
struct ListNode {
int val;
struct ListNode *next;
ListNode(int x) :
val(x), next(NULL) {
}
};*/
class Solution {
public:
ListNode* Merge(ListNode* pHead1, ListNode* pHead2)
{
if(!pHead1 || !pHead2)
return !pHead1 ? pHead2 : pHead1;
ListNode *head = NULL;
ListNode *p = NULL;
ListNode *p1 = pHead1;
ListNode *p2 = pHead2;
//确定头元素
if(pHead1->val < pHead2->val)
{
head = pHead1;
p1 = p1->next;
}
else
{
head = pHead2;
p2 = p2->next;
}
p = head;    //新链表的指针

while(p1 && p2)
{
if(p1->val < p2->val)
{
p->next = p1;
p1 = p1->next;
}
else{
p->next = p2;
p2 = p2->next;
}
p = p->next;
}
//这里跟合并数组不一样,数组用while
if(p1 != NULL)
{
p->next = p1;
}
else
p->next = p2;
return head;
}
};
用递归思想来解决问题会很容易,因为每加入一个结点,剩下的又相当于执行一次合并操作,注意终止条件。简洁递归:

/*
struct ListNode {
int val;
struct ListNode *next;
ListNode(int x) :
val(x), next(NULL) {
}
};*/
class Solution {
public:
ListNode* Merge(ListNode* pHead1, ListNode* pHead2)
{
if(pHead1 == NULL)
return pHead2;
else if(pHead2 == NULL)
return pHead1;

ListNode *mergeHead = NULL;
if(pHead1->val < pHead2->val)
{
mergeHead = pHead1;
mergeHead->next = Merge(pHead1->next, pHead2);
}
else{
mergeHead = pHead2;
mergeHead->next = Merge(pHead1, pHead2->next);
}
return mergeHead;
}
};
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息