C/C++语言重温------排序之归并排序

本文详细探讨了C/C++中归并排序的原理与实现,通过实例代码展示了如何使用归并排序对数组进行高效排序,揭示了其在复杂度分析上的优势,并讨论了适用场景和优化策略。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

C/C++语言重温------排序之归并排序


#include<iostream>

using namespace std;

// 模板获取数组长度的方法
template <typename T, int N>

int getSize(T(&input)[N]) {
	return sizeof(input) / sizeof(T);
}

// 定义数组长度为全局变量
int arr_length = 0;

// 输出数组
void display_arr(int *arr) 
{

	for (int i = 0; i < arr_length; i++)
	{
		cout << "arr[" << i << "]:" << arr[i] << endl;
	}
}

/*
	归并排序:         
		分治的思想:
			归并排序的核心思想是分治,把一个复杂问题拆分成若干个子问题来求解。

		归并排序的算法思想:
			把数组从中间划分为两个子数组;
			一直递归地把子数组分为更小的子数组,直到子数组里面只有一个元素;
			依次按照递归的返回顺序,不断地合并排序好地子数组,直到最后把整个数组的顺序拍好。

		时间复杂度: O(nlogn)

		空间复杂度:O(n)
			由于合并n个元素需要分配一个大小为n的额外数组,合并完成后,这个数组的空间就会被释放。
*/

// 归并排序递归函数主体
void merge_sort_recursive(int arr[], int arrCopy[], int start, int end) {
	

	if (start >= end)
		return;

	int len = end - start, mid = (len >> 1) + start;
	// 左半边数组起止位置
	int leftStart = start, leftEnd = mid;
	// 左半边数组起止位置
	int rightStart = mid + 1, rightEnd = end;

	// 左半边数组排序
	merge_sort_recursive(arr, arrCopy, leftStart, leftEnd);
	// 右半边数组排序
	merge_sort_recursive(arr, arrCopy, rightStart, rightEnd);

	int k = start;

	// 先比较两个数组,进行排序
	while (leftStart <= leftEnd && rightStart <= rightEnd) 
	{
		arrCopy[k++] = arr[leftStart] < arr[rightStart] ? arr[leftStart++] : arr[rightStart++];
	}

	// 接着将左边剩余元素或右边剩余元素放到数组尾部
	while (leftStart <= leftEnd)
	{
		arrCopy[k++] = arr[leftStart++];
	}

	while (rightStart <= rightEnd)
	{
		arrCopy[k++] = arr[rightStart++];
	}

	// 将排序好的数组复制给原数组
	for (k = start; k <= end; k++)
		arr[k] = arrCopy[k];
}


void merge_sort(int arr[], const int len) {

	// 开辟存放数组的空间
	int* arrCopy = (int*)malloc(len * sizeof(arr[0]));

	// 递归函数排序
	merge_sort_recursive(arr, arrCopy, 0, len - 1);
}


int main(int argc, char const *argv[])
{
	int arr[]  = { 5, 6, 1, 9, 2, 4, 3, 7, 10, 8 };

	arr_length = getSize(arr);

	display_arr(arr);
	
	// 归并排序
	merge_sort(arr, arr_length);

	display_arr(arr);

	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值