合并两个有序链表

方法1:递归求解

首先设两个单链表的头节点分别为head1、head2。如果head1为空,则直接返回head2,若head2为空,则直接返回head1。若head1与head2都不为空,则比较head1-.val 与head2->val的大小,来决定head1和head2谁为合并后的单链表的头节点。分两种情况:

1.若head1->val <= head2->val,则头节点head = head1,接着递归去求分别以head1->next 和 head2 为头节点的两个单链表的合并链表的子问题。

2.若head1->val > head2->val,则头节点head = head2,接着递归去求分别以head1 和 head2->next 为头节点的两个单链表的合并链表的子问题。


方法2:非递归求解

首先分别用指针head1,head2来遍历两个链表,如果当前head1->val <= head2->val,则将head1指向的节点归入到合并后的链表中;否则将head2指向的节点归入到合并后的链表中。当有一个链表遍历结束,则把尚未遍历完毕的链表直接链接到合并的链表尾部即可。


以下是上述两种方法的代码实现:

#include <iostream>
#include <vector>
#include <map>
using namespace std;

struct listNode
{
	int val;
	struct listNode *next;
};
// 方法1:递归法,返回一个指向排序后的链表的头指针
listNode * mergeRecursive(listNode *head1, listNode *head2){
	if (head1 == NULL){
		return head2;
	}
	if (head2 == NULL){
		return head1;
	}
	listNode *head = NULL;
	if (head1->val <= head2->val){
		head = head1;
		head->next = mergeRecursive(head1->next, head2);
	}
	else{
		head = head2;
		head->next = mergeRecursive(head1, head2->next);
	}
	return head;
}
// 方法2:非递归法求解
listNode *mergeListNode(listNode *head1, listNode *head2){
	listNode *cur = new listNode;
	cur->val = 999;
	cur->next = NULL;
	listNode *rst = cur;

	while (head1 != NULL && head2 != NULL){
		if (head1->val <= head2->val){
			cur->next = head1;
			cur = head1;
			head1 = head1->next;
		}
		else{
			cur->next = head2;
			cur = head2;
			head2 = head2->next;
		}
	}
	if (head1 != NULL){
		cur->next = head1;
	}
	if (head2 != NULL){
		cur->next = head2;
	}

	return rst->next;
}
// 打印单链表
void printList(listNode *head){
	listNode *cur = head;
	while(cur != NULL){
		cout << cur->val << " ";
		cur = cur->next;
	}
	cout << endl;
}

int main()
{
	// 先建立一个有6个节点的单链表1:0-1-3-5-7-9
	listNode *head1 = new listNode;
	head1->val = 0;
	int n = 1;
	listNode *cur1 = head1;
	while(n <= 9){
		cur1->next = new listNode;
		cur1 = cur1->next;
		cur1->val = n;
		n += 2;
	}
	cur1->next = NULL;
	cur1 = head1;
	n = 0;

	// 建立一个有6个节点的单链表2: -1-0-2-4-8-10
	listNode *head2 = new listNode;
	head2->val = -1;
	n = 0;
	listNode *cur2 = head2;
	while (n <=10){
		cur2->next = new listNode;
		cur2 = cur2->next;
		cur2->val = n;
		n += 2;
	}
	cur2->next = NULL;
	cur2 = head2;

	// 打印两单链表1,2
	printList(cur1);
	printList(cur2);

	listNode *result = mergeRecursive(cur1, cur2);
	cur1 = head1;
	cur2 = head2;
	cout << "利用递归法合并后的单链表为:" ;
	printList(result);

	// 先建立一个有6个节点的单链表3:0-1-3-5-7-9
	listNode *head3 = new listNode;
	head3->val = 0;
	int nn = 1;
	listNode *cur3 = head3;
	while(nn <= 9){
		cur3->next = new listNode;
		cur3 = cur3->next;
		cur3->val = nn;
		nn += 2;
	}
	cur3->next = NULL;
	cur3 = head3;

	// 建立一个有6个节点的单链表4: -1-0-2-4-8-10
	listNode *head4 = new listNode;
	head4->val = -1;
	nn = 0;
	listNode *cur4 = head4;
	while (nn <=10){
		cur4->next = new listNode;
		cur4 = cur4->next;
		cur4->val = nn;
		nn += 2;
	}
	cur4->next = NULL;
	cur4 = head4;

	// 打印两单链表3,4
	printList(cur3);
	printList(cur4);

	result = mergeListNode(cur3, cur4);
	cout << "利用非递归法合并后的单链表为:" ;
	printList(result);
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值