题目: 输入两个递增排序的链表,要求把两个链表和并成一个链表并且使得新链表也是递增排序的。
分析:
1. 假设两个链表如下所示
2. 要合并两个链表,可以利用归并排序的合并思想,从头枚举两个链表,判断两个指针指向的两个结点的值关系。
(1)初始化两个指针p1,p2分别指向两个链表的头结点,合并之后新的链表头结点肯定是两个链表中值较小的那个
(2)每一次比较两个指针指向的结点值的大小,如果p1较小则把p1指向结点加入新链表,否则加入p2指向的结点。直到有一个链表为空,然后把剩下的所有结点全部加入新链表即可
3. 代码(归并排序思想)
//链表结点
struct ListNode{
int value;
ListNode *nextNode;
};
//合并两个链表
ListNode* MergeList(ListNode *headOne, ListNode *headTwo){
//如果第一个链表是空链表返回链表2头结点
if(headOne == NULL){
return headTwo;
}
//如果第二个链表是空链表返回链表1头结点
if(headTwo == NULL){
return headOne;
}
//设定两个指针分别指向两个链表头结点
ListNode *p1 = headOne;
ListNode *p2 = headTwo;
ListNode *newHeadNode = NULL;
//判断哪一个是新的头结点
if((p1->value) <= (p2->value)){
newHeadNode = p1;
p1 = p1->nextNode;
}
else{
newHeadNode = p2;
p2 = p2->nextNode;
}
//设置一个指向新链表的指针
ListNode *curNode = newHeadNode;
//合并两个链表
while((p1 != NULL) && (p2 != NULL)){
if((p1->value) <= (p2->value)){
curNode->nextNode = p1;
curNode = curNode->nextNode;
p1 = p1->nextNode;
}
else{
curNode->nextNode = p2;
curNode = curNode->nextNode;
p2 = p2->nextNode;
}
}
//把剩下没有加入的全部加入新链表
//最多只会有一个链表不为空
while((p1 != NULL)){
curNode->nextNode = p1;
curNode = curNode->nextNode;
p1 = p1->nextNode;
}
while(p2 != NULL){
curNode->nextNode = p2;
curNode = curNode->nextNode;
p2 = p2->nextNode;
}
//返回新的链表结点
return newHeadNode;
}
递归代码,更加简洁
struct ListNode{
int value;
ListNode *nextNode;
};
//合并两个链表
ListNode* MergeList(ListNode *headOne, ListNode *headTwo){
//链表1为空
if(headOne == NULL){
return headTwo;
}
//链表2为空
if(headTwo == NULL){
return headOne;
}
//新建一个结点
ListNode *newNode = NULL;
if((headOne->value) <= (headTwo->value)){
newNode = headOne;
newNode->nextNode = MergeList(headOne->nextNode, headTwo);
}
else{
newNode = headTwo;
newNode->nextNode = MergeList(headOne, headTwo->nextNode);
}
return newNode;
}