C语言数据结构快速排序的非递归、归并排序、归并排序的非递归等的介绍

文章目录

  • 前言
  • 一、快速排序非递归
  • 二、归并排序
  • 五、归并排序非递归
  • 总结

前言

C语言数据结构快速排序的非递归、归并排序、归并排序的非递归等的介绍


一、快速排序非递归

快速排序非递归的定义

  • 快速排序非递归,需要使用栈来实现。
  • 将左右下标分别push到栈中。
  • 在栈为空之前,循环获取区间的中间值下标并同时将左右区间排序。
  • 判断若中间值下标(keyi) + 1小于end,则将此区间push到栈中。
  • 若begin 小于 中间值下标(keyi),则将此区间push到栈中。
  • 循环直到栈为空。
int PartSort3(int* a, int left, int right)
{
	int keyi = left;

	int prev = left;
	int cur = left + 1;


	while (cur <= right)
	{
		/*if (a[cur] < key)
		{
			prev++;
			Swap(&a[cur], &a[prev]);
		}
		cur++;*/

		if (a[cur] < a[keyi] && ++prev != cur)
			Swap(&a[cur], &a[prev]);
		cur++;
	}
	Swap(&a[prev], &a[keyi]);

	return prev;
}

// 快速排序非递归
void QuickSortNonR(int* a, int left, int right)
{
	int* tmp = (int*)malloc(sizeof(int) * (right - left + 1));
	ST st;
	STInit(&st);

	STPush(&st, right);
	STPush(&st, left);

	while (!STEmpty(&st))
	{
		int begin = STTop(&st);
		STPop(&st);
		int end = STTop(&st);
		STPop(&st);

		int keyi = PartSort3(a, begin, end);

		if (keyi + 1 < end)
		{
			STPush(&st, end);
			STPush(&st, keyi - 1);
		}

		if (begin < keyi - 1)
		{
			STPush(&st, keyi - 1);
			STPush(&st, begin);
		}
	}
	
	STDestroy(&st);
}
  • 其中PartSort3函数是快速排序快慢指针的单趟排序。

快速排序非递归测试

void TestQuickSortNonR()
{
	int a[] = { 9, 7, 6 ,4 ,8 ,3 ,5 ,1 ,2, 0 };

	PrintArray(a, sizeof(a) / sizeof(a[0]));

	QuickSortNonR(a, 0, sizeof(a) / sizeof(a[0]) - 1);

	PrintArray(a, sizeof(a) / sizeof(a[0]));
}

效果如下:
在这里插入图片描述

二、归并排序

归并排序定义

  • 直接将区间拆分成左右区间。
  • 左右区间分别递归直到单个数字,并在返回后归并左右区间到一个临时的数组中。
  • 然后将临时数组中的数字memcpy拷贝到原数组中。
// 归并排序
void _MergeSort(int* a, int left, int right, int* tmp)
{
	if (left >= right)
		return;
	int midi = left + (right - left) / 2;

	int begin1 = left, end1 = midi;
	int begin2 = midi + 1, end2 = right;


	_MergeSort(a, begin1, end1, tmp);
	_MergeSort(a, begin2, end2, tmp);

	int i = left;
	while (begin1 <= end1 && begin2 <= end2)
	{
		if (a[begin1] < a[begin2])
		{
			tmp[i++] = a[begin1++];
		}
		else
		{
			tmp[i++] = a[begin2++];
		}
	}

	while (begin1 <= end1)
	{
		tmp[i++] = a[begin1++];
	}

	while (begin2 <= end2)
	{
		tmp[i++] = a[begin2++];
	}

	memcpy(a + left, tmp + left, sizeof(int) * (right - left + 1));

}



void MergeSort(int* a, int n)
{
	int* tmp = (int*)malloc(sizeof(int) * n);
	if (tmp == NULL)
	{
		perror("MergeSort malloc");
		return;
	}


	int left = 0;
	int right = n - 1;

	_MergeSort(a, left, right, tmp);


	free(tmp);
}


归并排序测试

void TestMergeSort()
{
	int a[] = { 9, 7, 6 , 6, 4,4 ,8 ,3 ,5 ,1 ,2, 0, 5 };

	PrintArray(a, sizeof(a) / sizeof(a[0]));

	MergeSort(a, sizeof(a) / sizeof(a[0]));

	PrintArray(a, sizeof(a) / sizeof(a[0]));
}

效果如下:
在这里插入图片描述

五、归并排序非递归

归并排序非递归定义

  • 归并一部分拷贝一部分
void MergeSortNonR(int* a, int n)
{
	int* tmp = (int*)malloc(sizeof(int) * n);
	int gap = 1;
	while (gap < n)
	{
		int i = 0;
		for (i = 0; i < n; i += 2 * gap)
		{

			int begin1 = i, end1 = i + gap - 1;
			int begin2 = i + gap, end2 = i + 2 * gap - 1;

			if (end1 >= n || begin2 >= n)
			{
				break;
			}
			if (end2 >= n)
			{
				end2 = n - 1;
			}
			int j = i;

			while (begin1 <= end1 && begin2 <= end2)
			{
				if (a[begin1] < a[begin2])
				{
					tmp[j++] = a[begin1++];
				}
				else
				{
					tmp[j++] = a[begin2++];
				}
			}

			while (begin1 <= end1)
			{
				tmp[j++] = a[begin1++];
			}

			while (begin2 <= end2)
			{
				tmp[j++] = a[begin2++];
			}

			memcpy(a + i, tmp + i, sizeof(int) * (end2 - i + 1));
		}
		gap *= 2;
	}
	


	free(tmp);
	tmp = NULL;
}

归并排序非递归测试

void TestMergeSortNonR()
{
	int a[] = { 9, 7, 6 , 6, 4,4 ,8 ,3 ,5 ,1 ,2, 0, 5 };

	PrintArray(a, sizeof(a) / sizeof(a[0]));

	MergeSortNonR(a, sizeof(a) / sizeof(a[0]));

	PrintArray(a, sizeof(a) / sizeof(a[0]));
}

效果如下:
在这里插入图片描述


总结

C语言数据结构快速排序的非递归、归并排序、归并排序的非递归等的介绍

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/682641.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【ubuntu软件版本管理】利用update-alternatives管理ubuntu软件

​ 我们有的时候希望在安装了新软件之后保留旧版本的软件&#xff0c;比如希望保留旧版本的gcc&#xff0c;以防以前写的C编译出问题&#xff0c;这时候就需要版本管理软件update-alternatives。 ​ 在此之前我们需要先弄清楚&#xff0c;什么是ubuntu的软件&#xff1f;拿C源…

微服务开发与实战Day02 - Docker

一、Docker快速入门 快速构建、运行、管理应用的工具 安装部署教程&#xff1a;Docs 1. 部署MySQL 测试连接&#xff1a; 镜像和容器 当我们利用Docker安装应用时&#xff0c;Docker会自动搜索并下载应用镜像&#xff08;image&#xff09;。镜像不仅包含应用本身&#xff…

Go微服务: 基于rocketmq:5.2.0搭建RocketMQ环境,以及示例参考

概述 参考最新官方文档&#xff1a;https://rocketmq.apache.org/zh/docs/quickStart/03quickstartWithDockercompose以及&#xff1a;https://rocketmq.apache.org/zh/docs/deploymentOperations/04Dashboard综合以上两个文档来搭建环境 搭建RocketMQ环境 1 ) 基于 docker-c…

RTOS笔记--任务状态与调度

任务状态 freertos中的任务分为四个状态&#xff1a;就绪状态&#xff08;ready&#xff09;、运行状态&#xff08;running&#xff09;、阻塞状态&#xff08;blocked&#xff09;、暂停状态&#xff08;suspended&#xff09; 完整的任务状态转换图&#xff1a; 在使用vTas…

04--Tomcat

前言&#xff1a;本章整理tomcat的知识点&#xff0c;tomcat知识点相较nginx比较少&#xff0c;但是也是运维必会的软件&#xff0c;这里结合实际项目整理一下。 1、tomcat简介 Tomcat 服务器是一个免费的开放源代码的Web 应用服务器&#xff0c;属于轻量级应用服务器&#x…

在线建站流程分析

建站流程是指通过互联网创建一个个人或企业网站的过程。随着互联网的发展&#xff0c;越来越多的人和机构开始意识到网络的重要性&#xff0c;建站成为一种常见的行为。在线建站的流程一般包括以下几个步骤。 首先&#xff0c;选择一个合适的建站平台。目前&#xff0c;有很多在…

英伟达Docker 安装与GPu镜像拉取

获取nvidia_docker压缩包nvidia_docker.tgz将压缩包上传至服务器指定目录解压nvidia_docker.tgz压缩包 tar -zxvf 压缩包执行rpm安装命令&#xff1a; #查看指定rpm包安装情况 rpm -qa | grep libstdc #查看指定rpm包下的依赖包的版本情况 strings /lib64/libstdc |grep GLI…

这才是大模型价格战背后的真相

想必大家今天肯定被各家大模型厂商的降价新闻刷圈了&#xff0c;如果说 Meta Llama 3 的开源是国外大模型市场的搅局者&#xff0c;那 DeepSeek-V2 就是国内大模型市场的鲶鱼&#xff0c;但是价格战背后是大模型基础设施优化带来的物美价廉&#xff0c;还是浑水摸鱼的噱头&…

数据结构——(java版)包装类与泛型

文章目录 一 包装类1.1 包装类的概念1.2 装箱/装包1.3 拆箱/拆包1.4 一个面试题&#xff1a; 二 泛型2.1 什么是泛型&#xff1f;2.2 泛型的使用2.3 泛型的上界2.4 泛型实现Comparable接口2.5 擦除机制另外&#xff1a; 一 包装类 1.1 包装类的概念 在java中基本数据类型并不…

中国自动气象站:现代气象观测的中流砥柱

引言 气象观测是人类认识和预报天气的重要手段。在现代科技的推动下&#xff0c;自动气象站成为气象观测的重要工具&#xff0c;为天气预报、防灾减灾和气候研究提供了宝贵的数据支持。本文将介绍中国自动气象站的发展历程、技术特点及其在气象观测中的重要作用。 中国自动气象…

【Linux】信号(一)

信号我们将从信号产生&#xff0c;信号的保存&#xff0c;信号处理分别进行讲解~ 至少大思路是这样。开始之前还要进行一些基础知识的铺垫。 目录 从生活中提炼一些结论&#xff1a;信号概念的一些储备&#xff1a;信号产生&#xff1a;一、kill指令&#xff1a;二、键盘组合键…

BP 客户主数据-国际贸易条款发生更改

Issue &#xff1a;ECC升级S4后 1&#xff09;客户主数据扩产线时(LHGX03)&#xff0c;国贸条件2变更记录查询时&#xff0c;所扩产线&#xff08;30 1C&#xff09;无变更记录&#xff0c;未变更产线&#xff08;10 1C/1H/1M&#xff09;确认变更记录 20230108新增&#xff1…

生命在于学习——Python人工智能原理(3.2)

三、深度学习 &#xff08;二&#xff09;人工神经网络 人工神经网络是模仿人类大脑神经系统工作原理所创建的数学模型&#xff0c;有并行的分布处理能力、高容错性和自我学习等特征。 1、感知器 感知器由Frank Roseblatt于1957年提出&#xff0c;是一种广泛使用的线性分类…

Matlab解决矩阵微分方程建模(代码开源)

#用matlab解决施密特正交规范化矩阵之后&#xff0c;我又想到矩阵的微分方程计算量真的太大了&#xff0c;来回转化让我头大&#xff0c;于是我尝试了一下用matlab建立模型来解决这类问题。 代码部分如下&#xff1a;注解还挺清晰的&#xff1a; %%%解微分方程组%eg&#xff…

多目标优化-NSGA-II

文章目录 一、前置知识NSGA-II帕累托前沿 二、算法流程1.NSGA2.NSGA-II 一、前置知识 1.NSGA(非支配排序遗传算法):旨在同时优化多个冲突的目标函数&#xff0c;寻找帕累托前沿上的解集。 什么是多个冲突的目标: 比如你看上了一辆车&#xff0c;你既想要它便宜&#xff0c;又…

一个思维狂赚20万+?揭秘电商平台隐藏的流量认知!

你想要的流量&#xff0c;资源&#xff0c;人脉&#xff0c;都已经有人为你准备&#xff0c;你只需要找到拥有这些资源的人。对于流量和信息&#xff0c;也是一样&#xff0c;你想找的客户和产品&#xff0c;都已经有人为你准备在淘宝、拼多多等电商平台&#xff0c;你只需要找…

掌握Postman,轻松调试POST与GET接口:详细安装与实战教程,让你的API测试更高效

0.前言 在确保数据接口的稳定性和可访问性方面&#xff0c;使用专业的接口测试工具至关重要。这些工具不仅简化了测试流程&#xff0c;还提供了无需编写额外代码即可轻松调用和调试接口的能力&#xff0c;从而大大提高了测试效率和准确性。 0.1 Postman 背景介绍 用户在开发或…

遭遇Device Association Service占用CPU和内存过高异常

1.异常描述 在蓝牙设备搜索和配对过后&#xff0c;系统界面卡住了&#xff0c;查找了下任务管理器&#xff0c;发现有一个主机服务占用了过多的CPU和内存&#xff0c;且不断的在增长。截图如下&#xff1a; 百度查了下&#xff0c;Device Association Service是一个Win10系统服…

HCIP-Datacom-ARST自选题库_10_多种协议多选【24道题】

1.如图所示&#xff0c;PE1和PE2之间通过LoopbackO接口建立MP-BGP邻居关系&#xff0c;在配完成之后&#xff0c;发现CE1和CE2之间无法互相学习路由&#xff0c;下列哪些选项会造成该问题的出现? PE1或PE2未在BGP-VPNV4单播地址族视图使能邻居A PE1或PE2上的VPN实例参数配置错…

JVM的内存结构

JVM 内存结构 方法区: 方法区主要用于存储虚拟机加载的类信息、常量、静态变量&#xff0c;以及编译器编译后的代码等数据。 程序计数器 由于在JVM中&#xff0c;多线程是通过线程轮流切换来获得CPU执行时间的&#xff0c;因此&#xff0c;在任一具体时刻&#xff0c;一个CP…