结点定义如下
/**
* Definition for singly-linked list.
* 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:
ListNode *mergeTwoLists(ListNode *l1, ListNode *l2)
{
//首先判断是否为空
if (l1 == NULL && l2 == NULL)
return NULL;
if (l1 != NULL && l2 == NULL)
return l1;
if (l1 == NULL && l2 != NULL)
return l2;
//这一步太过麻烦实际上只需要两个if即可。
ListNode *newlist;
ListNode *listhead;
//问题在于记录头结点,这里我用的办法是先把头结点找出来但是多了一次
//判断。不够简练。可以采用初始设定一个头结点,最后只需要返回next
if (l1->val < l2->val)
{
newlist = l1;
l1 = l1->next;
}
else
{
newlist = l2;
l2 = l2->next;
}
listhead = newlist;
//这里重复设置了l1_move和l2_move两个变量,实际没有必要。
//因为一开始我的判定条件搞错了,所以才糊涂了
ListNode *l1_move = l1;
ListNode *l2_move = l2;
while (l1 != NULL && l2 != NULL)
{
if (l1->val < l2->val)
{
l1_move = l1;
l1 = l1->next;
newlist->next = l1_move;
}
else
{
l2_move = l2;
l2 = l2->next;
newlist->next = l2_move;
}
newlist = newlist->next;
}
if (l1 == NULL)
newlist->next = l2;
else
newlist->next = l1;
//这一步依旧可以用一个表达式写出来
return listhead;
}
};
下面是第二版
class Solution
{
public:
ListNode *mergeTwoLists(ListNode *l1, ListNode *l2)
{
ListNode listhead(-1);//设置一个初始结点,不用设置初始结点
ListNode *newlist = &listhead;
while (l1 != NULL && l2 != NULL)
{
if (l1->val < l2->val)
{
newlist->next = l1;
l1 = l1->next;
}
else
{
newlist->next = l2;
l2 = l2->next;
}
newlist = newlist->next;
}
//开始的判断也不用了,因为和最后面的判断条件结果均一样
newlist->next = l1 != NULL ? l1 : l2;
return listhead.next;
}
};