题目描述
输入两个单调递增的链表,输出两个链表合成后的链表,当然我们需要合成后的链表满足单调不减规则。
eg:
输入 | {1,3,5},{2,4,6} |
---|---|
输出 | {1,2,3,4,5,6} |
题外话:小范说合在一起,再比大小不就完事了,这显然是一个简单的方法,但不智能。
【官方解法】
1.迭代版本求解
初始化:定义cur指向新链表的头结点
操作:
1.如果l1指向的结点值小于等于l2指向的结点值,则将l1指向的结点值链接到cur的next指针,然后l1指向下一个结点值
2.否则,让l2指向下一个结点值
3.循环步骤1,2,直到l1或者l2为nullptr
4.将l1或者l2剩下的部分链接到cur的后面
技巧
一般创建单链表,都会设一个虚拟头结点,也叫哨兵,因为这样每一个结点都有一个前驱结点。
/*
struct ListNode {
int val;
struct ListNode *next;
ListNode(int x) :
val(x), next(NULL) {
}
};*/
class Solution {
public:
ListNode* Merge(ListNode* pHead1, ListNode* pHead2)
{
ListNode* vhead = new ListNode(-1);//虚拟头节点创建,实例成任何一个数字都可以,-1 0 2 等
ListNode* cur = vhead;
while (pHead1 && pHead2) {
if (pHead1->val <= pHead2->val) {
cur->next = pHead1;
pHead1 = pHead1->next;
}
else {
cur->next = pHead2;
pHead2 = pHead2->next;
}
cur = cur->next;
}
cur->next = pHead1 ? pHead1 : pHead2;//判断pHead1是否有值,如果有则指向p1否则指向p2
return vhead->next; //返回虚拟头节点的next
}
};
对于这三行额外的解释(前面欠下的章,现在解释清楚了~~~):
{ ListNode* vhead = new ListNode(-1);//创建一个空节点,val为-1,当然其他值也可以
ListNode* cur = vhead; //把头节点vhead的信息给cur,用cur来代替vhead工作,
//这是由于下面的while里面的cur是在变化的。
//相当于for(int i = 0;i<10;i++)中的i
。。。。。
}
return vhead->next;//正确的结果是vhead的next中的结果
2.递归版本
class Solution {
public:
ListNode* Merge(ListNode* pHead1, ListNode* pHead2)
{
if (!pHead1) return pHead2;
if (!pHead2) return pHead1;
if (pHead1->val <= pHead2->val) {
pHead1->next = Merge(pHead1->next, pHead2);
return pHead1;
}
else {
pHead2->next = Merge(pHead1, pHead2->next);
return pHead2;
}
}
};