面试题76:单链表的归并排序

时间复杂度:O(nlgn)

#include <iostream>
#include <string>
using namespace std;

/*
MergeSort(headRef)
1) If head is NULL or there is only one element in the Linked List
then return.
2) Else divide the linked list into two halves.
FrontBackSplit(head, &a, &b); // a and b are two halves 
3) Sort the two halves a and b.
MergeSort(a);
MergeSort(b);
4) Merge the sorted a and b(using SortedMerge() discussed here)
and update the head pointer using headRef.
*headRef = SortedMerge(a, b);
*/

struct Node{
	int val;
	Node *next;
	Node(int _val) :val(_val), next(NULL){}
};

void FrontBackSplit(Node *head, Node **a, Node **b)
{
	if (head == NULL || head->next == NULL) return;
	Node *faster = head->next;
	Node *slower = head;
	while (faster && faster->next)
	{
		slower = slower->next;
		faster = faster->next->next;
	}
	*b = slower->next;
	slower->next = NULL;
	*a = head;
}

Node *SortedMerge(Node *a, Node *b)
{
	if (a == NULL) return b;
	if (b == NULL) return a;
	Node *head = NULL;
	if (a->val < b->val)
	{
		head = a;
		a = a->next;
	}
	else{
		head = b;
		b = b->next;
	}
	Node *pNext = head;
	while (a && b)
	{
		if (a->val < b->val)
		{
			pNext->next = a;
			a = a->next;
		}
		else
		{
			pNext->next = b;
			b = b->next;
		}
		pNext = pNext->next;
	}
	if (a) pNext->next = a;
	else pNext->next = b;
	return head;
}


void MergeSort(Node **head)
{
	if (!(*head) || !(*head)->next) return;
	Node *a = NULL, *b = NULL;
	FrontBackSplit(*head, &a, &b);
	MergeSort(&a);
	MergeSort(&b);
	*head = SortedMerge(a, b);
}

//main函数进行测试 
int main()
{
	Node *n1 = new Node(2);
	Node *n2 = new Node(1);
	Node *n3 = new Node(4);
	Node *n4 = new Node(3);
	Node *n5 = new Node(5);
	n1->next = n2;
	n2->next = n3;
	n3->next = n4;
	n4->next = n5;
	MergeSort(&n1);
	while (n1)
	{
		cout << n1->val << " ";
		n1 = n1->next;
	}
	cout << endl;
	return 0;
}


  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值