排序算法——梳理总结

✨冒泡
✨选择
✨插入
 ✨标准写法
 🎭不同写法
✨希尔排序——标准写法
✨快排
✨归并
✨堆排

在这里插入图片描述

冒泡

在这里插入图片描述

void Bubble(vector<int>& nums)
{
	// 冒泡排序只能先确定最右边的结果,不能先确定最左边的结果
	for (int i = 0; i < nums.size(); i++)
	{
	// 确定的右边的就不用排了并且不能让j+1越界
	// 所以判断条件是nums.size()-i - 1
		for (int j = 0; j < nums.size()-i - 1; j++)
			if (nums[j] > nums[j + 1])
				swap(nums[j], nums[j + 1]);
	}
}

选择

选择排序重要的是选,先选出来,再将这个数交换进去
在这里插入图片描述

void Select(vector<int>& nums)
{
	for (int i = 0; i < nums.size(); i++)
	{
		int t = i;// 记录需要交换的数的位置
		for (int j = i + 1; j < nums.size(); j++)
			if (nums[t] > nums[j])
				t = j;
		swap(nums[t], nums[i]);
	}
}

插入

在这里插入图片描述

标准写法

插入排序是一个一个往后挪,最后再插入

void Insert(vector<int>& nums)
{
	for (int i = 0; i < nums.size(); i++)
	{
		int t = nums[i];
		// 注意j表示需要检查的位置,这个位置必须遵循j>=0
		for (int j =i-1; j >= 0; j--)
		{
			if (nums[j] > t)
				nums[j + 1] = nums[j];
			else
			{
				nums[j + 1] = t;
				break;
			}
		}
	}
}

注意j的范围

🎭不同写法

这种写法类似于冒泡排序,他是往前冒,虽然能对,但是这已经不是插入排序的思想

int* sortArray(int* nums, int numsSize, int* returnSize)
{
    //插入排序:在已经排好序的数组中进行插入
    *returnSize=numsSize;
    for(int i=0;i<numsSize;i++)
    {
        //从此位置向前比
        for(int j=i;j>0;j--)
        {
            if(nums[j]<nums[j-1])
            {
                int tem=nums[j];
                nums[j]=nums[j-1];
                nums[j-1]=tem;
            }
            else
            break;
        }
    }
    return nums;
}

希尔——标准写法

在这里插入图片描述

希尔排序是在插入排序的基础上发展而来,所以要遵循插入排序的逻辑
他和插入排序不同在于,插入排序的gap=1,这个gap是从大到小变化

void Shell(vector<int>& nums)
{
	for (int gap = nums.size()/2; gap >0; gap/=2)// 间隔	
	{
	//每次向后跳间隔个长度
		for (int i = 0; i < nums.size(); i++) 
		{
			int t = nums[i];
			// 注意j的范围
			for (int j = i-gap; j >= 0; j -= gap)
			{
				if (nums[j] > t)
					nums[j + gap] = nums[j];
				else
				{
					nums[j + gap] = t;
					break;
				}
			}

		}
	}
}

注意j的范围


快排

我们使用三段式进行排序
[l,left] [left+1,right-1] [right,r]
[l,left]——小于key
[left + 1 , right-1]—— 等于key,等于key的是不用排序
[right , r]——大于key

int getNum(vector<int>& nums, int l, int r)
{
	srand(time(nullptr));
	return nums[l + rand() % (r - l + 1)];
}
void quicksort(vector<int>& nums, int l, int r)
{
	if (l >= r) return;
	int key = getNum(nums, l, r);
	int left = l - 1, right = r + 1, g = l;// 采用三段式进行
	while (g < right)
	{
		if (nums[g] == key) g++;
		else if (nums[g] < key) swap(nums[g++], nums[++left]);
		else swap(nums[g], nums[--right]);
	}
	// [l,left][left+1,right-1][right,r]
	quicksort(nums, l, left), quicksort(nums, right, r);
}

归并

归并排序需要一个辅助数组,我们使用的是vector,使用之前需要进行resize,开足够大的空间的同时要运行进行随机访问

vector<int> tem;
void mergesort(vector<int>& nums, int l, int r)
{
	if (l >= r) return;
	int mid = l + r >> 1;
	mergesort(nums, l, mid), mergesort(nums, mid + 1, r);
	int left = l, right = mid + 1;
	int t = 0;
	while (left <= mid && right <= r)
	{
		if (nums[left] < nums[right]) tem[t++] = nums[left++];
		else tem[t++] = nums[right++];
	}
	while (left <= mid) tem[t++] = nums[left++];
	while (right <= r) tem[t++] = nums[right++];
	t = 0;
	left = l;
	while (left <= r) nums[left++] = tem[t++];
}

堆排

void up(vector<int>& nums,int t)
{
	while (t > 0)
	{
		int parent = (t - 1) / 2;
		// 大根堆
		if (nums[parent] < nums[t])
			swap(nums[parent], nums[t]);
		t = parent;
	}
}
void down(vector<int>& nums,int t)
{
	// 需要从这个位置开始向下down到底
	int child = t * 2 + 1;
	while (child < nums.size())
	{
		// 找到左右孩子中最小的位置
		//if (child + 1 < nums.size() && nums[child] > nums[child + 1])
		//	child++;
		//if(nums[t]>nums[child]) 
		//	swap(nums[t], nums[child]);

		if (child + 1 < nums.size() && nums[child] < nums[child + 1]) child++;
		if (nums[t] < nums[child])
			swap(nums[t], nums[child]);
		t = child;
		child = t * 2 + 1;
	}
}
void Heap(vector<int>& nums)
{
	 //筛选法建立初始堆——小大根堆都可以
	//for (int i = nums.size()/2; i >= 0; i--) down(nums, i);
	//for (int i = 0 ; i < nums.size(); i++) up(nums, i);// 如果想用up初始化堆,只能从头开始
}
  1. 筛选法建堆——先将所有数据加入构成堆,在从中间位置开始进行down(只能down,不论是建大堆还是小堆)
    什么时候使用up,为什么up不能在筛选法建堆中使用
    请添加图片描述
    就像上图中的情况,在建小堆的过程中,2是一定不能访问到的,就不能建成小堆,所以不能在筛选法中使用up(关键是筛选法起点是中间位置)
    如果想使用up,必须将每一个进行up,或者是某个位置上面的已经成堆,那么就可以在这个位置直接使用up
    对于down来说,如果某个位置下面已经成堆,那么就可以直接使用down

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

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

相关文章

Effective C++ 学习笔记 条款16 成对使用new和delete时要采取相同形式

以下动作有什么错&#xff1f; std::string *stringArray new std::string[100]; // ... delete stringArray;每件事看起来都井然有序&#xff0c;使用了new&#xff0c;也搭配了对应的delete。但还是有某样东西完全错误&#xff1a;你的程序行为未定义。至少&#xff0c;str…

自律篇001-养成自律的秘密武器1-目标规划表

&#x1f680;以前在某书上看到一些博主非常自律&#xff0c;比如每天5点多起床看书&#xff0c;或者每天坚持健身&#xff0c;直到练出马甲线&#xff0c;还有一边工作一边考研等等&#xff0c;自己也曾尝试过做一些目标规划&#xff0c;但结果都不尽人意。写计划的时候往往信…

阿里云k8s环境下,因slb限额导致的发布事故

一、背景 阿里云k8s容器&#xff0c;在发布java应用程序的时候&#xff0c;客户端访问出现500错误。 后端服务是健康且可用的&#xff0c;网关层大量500错误请求&#xff0c;slb没有流入和流出流量。 经过回滚&#xff0c;仍未能解决错误。可谓是一次血的教训&#xff0c;特…

UI学习 一

教程&#xff1a;Accessibility – Material Design 3 需要科学上网&#xff0c;否则图片显示不出来。设计教程没有图片说明&#xff0c;不容易理解。 优化UI方向 清晰可见的元素足够的对比度和尺寸重要性的明确等级一眼就能辨别的关键信息 传达某一事物的相对重要性 将重…

简单了解Stable Diffusion里面sampling methods(采样方法)每种方法的效果

在 Stable Diffusion 模型中&#xff0c;采样方法&#xff08;Sampling Methods&#xff09;是指在生成图像时用于从模型的概率分布中抽取样本的算法。这些方法对于生成图像的质量、多样性和速度都有重要影响&#xff0c;以下是一些 Stable Diffusion 中常见的采样方法。 那么…

STM32day2

1.思维导图 个人暂时的学后感&#xff0c;不一定对&#xff0c;没什么东西&#xff0c;为做项目奔波中。。。1.使用ADC采样光敏电阻数值&#xff0c;如何根据这个数值调节LED灯亮度。 while (1){/* USER CODE END WHILE *//* USER CODE BEGIN 3 */adc_val HAL_ADC_GetValue(&a…

2575. 找出字符串的可整除数组(Go语言)

https://leetcode.cn/problems/find-the-divisibility-array-of-a-string/ 在看题解之前&#xff0c;我的代码是以下这样&#xff1a; package mainimport ("fmt" )func main() {fmt.Println(divisibilityArray("998244353", 3)) }func divisibilityArray…

基于LSTM实现春联上联对下联

按照阿光的项目做出了学习笔记&#xff0c;pytorch深度学习实战项目100例 基于LSTM实现春联上联对下联 基于LSTM&#xff08;长短期记忆网络&#xff09;实现春联上联对下联是一种有趣且具有挑战性的任务&#xff0c;它涉及到自然语言处理&#xff08;NLP&#xff09;中的序列…

【嵌入式】嵌入式系统稳定性建设:静态代码扫描的稳定性提升术

1. 概述 在嵌入式系统开发过程中&#xff0c;代码的稳定性和可靠性至关重要。静态代码扫描工具作为一种自动化的代码质量检查手段&#xff0c;能够帮助开发者在编译前发现潜在的缺陷和错误&#xff0c;从而增强系统的稳定性。本文将介绍如何在嵌入式C/C开发中使用静态代码扫描…

【数据结构】栈和队列的应用——括号匹配 + 表达式求值 + 表达式转换 +栈的递归应用+队列在计算机系统中的应用

文章目录 3.栈的应用3.1 括号匹配问题3.2 表达式求值3.2.1 三种算术表达式3.2.2 后缀表达式A.中缀转后缀B.后缀表达式的计算 3.2.3 前缀表达式A.中缀转前缀B.前缀表达式的计算 3.2.4 中缀表达式的求值 3.3 递归中栈的应用 4.队列的应用 栈基础知识&#xff1a;【数据结构】栈 顺…

react tab选项卡吸顶实现

react tab选项卡吸顶实现&#xff0c;直接上代码&#xff08;代码有注释&#xff09; tsx代码 /* eslint-disable react-hooks/exhaustive-deps */ import React, { useEffect, useState } from "react"; import DocumentTitle from react-document-title import s…

python界面开发 - Menu (popupmenu) 右键菜单

文章目录 1. python图形界面开发1.1. Python图形界面开发——Tkinter1.2. Python图形界面开发——PyQt1.3. Python图形界面开发——wxPython1.4. Python图形界面开发—— PyGTK&#xff1a;基于GTK1.5. Python图形界面开发—— Kivy1.6. Python图形界面开发——可视化工具1.7. …

交友盲盒系统PHP开源的盲盒源码

源码介绍&#xff1a; 交友盲盒系统是一款基于PHP开发的开源免费盲盒系统&#xff0c;旨在为用户提供一个充满乐趣和惊喜的社交体验。该系统具有丰富的功能和灵活的扩展性&#xff0c;可以轻松地满足各种线上交友、抽奖活动等场景的需求。 安装说明&#xff1a; PHP版本&…

鸿蒙Harmony应用开发—ArkTS声明式开发(基础手势:CheckboxGroup)

多选框群组&#xff0c;用于控制多选框全选或者不全选状态。 说明&#xff1a; 该组件从API Version 8开始支持。后续版本如有新增内容&#xff0c;则采用上角标单独标记该内容的起始版本。 子组件 无 接口 CheckboxGroup(options?: CheckboxGroupOptions) 创建多选框群组…

以人为本的AI技术升级

我们需要以人为本的技术来提高生产力和投资回报率。 通过在数据标注流程中融合机器学习辅助技术&#xff0c;可以减少数据标注所需的时间、资金和人力。 有很多方法可以防止标注员被模型的预测误导。 在传统的机器学习&#xff08;Machine Learning&#xff09;方法下&#…

阿珊比较Vue和React:两大前端框架的较量

&#x1f90d; 前端开发工程师、技术日更博主、已过CET6 &#x1f368; 阿珊和她的猫_CSDN博客专家、23年度博客之星前端领域TOP1 &#x1f560; 牛客高级专题作者、打造专栏《前端面试必备》 、《2024面试高频手撕题》 &#x1f35a; 蓝桥云课签约作者、上架课程《Vue.js 和 E…

【HarmonyOS】ArkTS-箭头函数

箭头函数 箭头函数是 比普通函数 更简洁 的一种函数写法 () > {}() > {// 函数体 }let 函数名 () > {// 函数体 }let 函数名 () > {// 函数体 } 函数名(实参1, 实参2)let 函数名 (形参1: 类型, 形参2: 类型) > {// 函数体 } 函数名(实参1, 实参2)let 函数名 …

99.qt qml-单例程序实现

在之前讲过: 58.qt quick-qml系统托盘实现https://nuoqian.blog.csdn.net/article/details/121855993 由于,该示例只是简单讲解了系统托盘实现,并没有实现单例程序,所以多次打开后就会出现多个exe出现的可能,本章出一章QML单例程序实现, 多次打开始终只显示出第一个打开…

1.5如何缓解图像分类任务中训练数据不足带来的问题?

1.5 图像数据不足时的处理方法 场景描述 在机器学习中&#xff0c;绝大部分模型都需要大量的数据进行训练和学习(包括有监督学习和无监督学习)&#xff0c;然而在实际应用中经常会遇到训练数据不足的问题。 比如图像分类&#xff0c;作为计算机视觉最基本的任务之一&#xff0…

Bytebase 签约合思,覆盖多云数据库变更发布,数据访问控制,安全治理的全生命周期,确保符合合规审计要求

在数字化快速发展时代&#xff0c;有效的规范数据库管理对企业安全运营至关重要。近日&#xff0c;数据库 DevOps 团队协同管理工具 Bytebase 签约费控领域领军企业合思&#xff0c;旨在全面优化数据库操作管理&#xff0c;收口全体员工的变更和查询操作&#xff0c;以提高整体…