快排C语言三种实现方法(大同小异)
快速排序C语言版(附带视频讲解)
注:3种快排的名字是我自己取的,并非专业名称
方法一(最常用的方法):左端抽轴(pivot)法
思路 && 操作:
- 排序准备:取左边第一位数为pivot轴,即pivot = a[0],
再令left = a[0],right = a[N-1] - 排序过程:此时从右端(right)开始,比较right对应的数
与pivot轴的大小,如果右边比pivot大(a[right] > pivot)
下标左移(right–),反之,将a[right]放在a[left]位置 - 完成一次操作(PartSort())循环结束条件为:left != right
- 递归函数进入条件:left < right
视频讲解:请点击->动画
代码如下:
#include <stdio.h>
#define N 15int PartSort(int * a, int left, int right);
void QuickSort(int * a, int left, int right);
void Print(int * a);int main(void)
{int i, a[N] = {5, 8, 1, 7, 4, 9, 48, 14, 0, 99, 45, 2, 84, 65, 6};printf("Before sort:\n");Print(a);printf("\nAfter sort:\n");QuickSort(a, 0, N-1);Print(a);return 0;
}int PartSort(int * a, int left, int right)
{int pivot = a[left];while (left != right){while (left < right && a[right] >= pivot)right --;a[left] = a[right];while (left < right && a[left] <= pivot)left ++;a[right] = a[left];}a[left] = pivot;return left;
}void QuickSort(int * a, int left, int right)
{int mid = 0;if (left < right){mid = PartSort(a, left, right);QuickSort(a, left, mid-1);QuickSort(a, mid+1, right);}return;
}void Print(int * a)
{int i;for (i = 0; i < N; i ++)printf("%d ", a[i]);printf("\n");return;
}
运行结果如下:
方法二:右端基准(basic)法
思路 && 操作:
- 排序准备:选取最右端数字为basic(基准),最左端标记为L(left),
右端倒数第二个数标记为R(right) - 排序过程:从左端开始,L指向的数比basic所指数小,则L向后移动一位(left++)
否则则停下;后,右端开始出发,如果R所指向的数字比basic大,则R向前移动
一位(right–),直到R也停下,此时将二者对应的数字进行交换,L后移,R前移
各一位完毕后,再从左端开始重复以上操作 - 完成一次操作(PartSort())循环结束条件为 :left < rigt(而非left != rigt)
因为数字交换导致的L和R分别进位可能会导致二者"擦肩而过",永世不得相遇 - 递归函数进入条件为:left < right 代码如下
视频讲解:请点击->动画
注:该视频所讲述略有瑕疵,视频中说L(left)与R(right)相遇后,L与R所指的同一个数(a)要与basic基准交换。实际上,交不交换取决于该数(a)与basic的大小,如果该数(a)大于basic基准,肯定要作交换,但是反之,就不能直接交换了,需要用该数(a)的下一个数与basic交换,想想为什么
举个例子:3 2 1 5(basic) —进行操作— 3 2 1 5(basic)
L R ----doing… — L&R
这个时候1 就不能和 5 换位置,换了就变成 3 2 5 1,1比5小怎么在5右侧?
实际上:每一次的basic的轴都是将一组数分割成两组的中心轴!
代码如下:
#include <stdio.h>
#define N 15 void Swap(int * a, int left, int basic);
int PartSort(int * a, int left, int right);
void QuickSort(int * a, int left, int right);
void Print(int * a);int main(void)
{int a[N] = {5, 8, 1, 7, 4, 9, 48, 14, 0, 99, 45, 2, 84, 65, 6};printf("Before sort:\n");Print(a);QuickSort(a, 0, N-1);printf("\nAfter sort:\n");Print(a);return 0;
} void Swap(int * a, int left, int param)
{int temp;temp = a[left];a[left] = a[param];a[param] = temp;return;
}int PartSort(int * a, int left, int right)
{int basic = right --;while (left < right){while (left < right && a[left] <= a[basic])left ++;while (left < right && a[right] >= a[basic])right --;if (left != right) {Swap(a, left, right);left ++;right --;}}if (a[left] > a[basic]) Swap(a, left, basic);else Swap(a, ++ left, basic);return left;
}void QuickSort(int * a, int left, int right)
{int mid = 0;if (left < right){mid = PartSort(a, left, right);QuickSort(a, left, mid-1);QuickSort(a, mid+1, right);}return;
}void Print(int * a)
{int i;for (i = 0; i < N; i ++)printf("%d ", a[i]);printf("\n");return;
}
运行结果如下:
方法三:快慢指针(i,j)法
思路 && 操作:
- 排序准备:快慢指针的构建,i为慢指针,j为快指针;取最右端为pivot轴
指针初始位置为: j为最左端,i为j的前一位(没错,刚开始i不对应数字) - 排序过程:如果快指针j对应的数字比pivot小,则慢指针i前进1位, 然后将
快慢指针对应的值进行交换;如果快指针j对应的数字比pivot大,则慢指针i
不动最后,将慢指针右1位的数字(即i+1)对应的数字与pivot轴进行交换 - 完成一次操作(PartSort())循环结束条件为:快指针小于pivot轴位置(即j < pivot)
- 递归函数进入条件:start < end
视频讲解:请点击->视频
代码如下:
#include <stdio.h>
#define N 15void QuickSort(int * a, int start, int end);
int PartSort(int * a, int start, int end);
void Swap(int * a, int i, int j);
void Print(int * a);int main(void)
{int a[N] = {5, 8, 1, 7, 4, 9, 48, 14, 0, 99, 45, 2, 84, 65, 6};printf("Before sort:\n");Print(a);QuickSort(a, 0, N-1);printf("\nAfter sort:\n");Print(a); return 0;
} void QuickSort(int * a, int start, int end)
{int mid = 0;if (start < end){mid = PartSort(a, start, end);QuickSort(a, start, mid-1);QuickSort(a, mid+1, end); } return;
}int PartSort(int * a, int start, int end)
{int i = start - 1;int j = start, pivot = end;for (; j < end; j ++){if (a[j] < a[pivot]){i ++;Swap(a, i, j);}}Swap(a, i + 1, pivot);pivot = i + 1; return pivot;
}void Swap(int * a, int i, int j)
{int temp;temp = a[i];a[i] = a[j];a[j] = temp;return;
}void Print(int * a)
{int i;for (i = 0; i < N; i ++)printf("%d ", a[i]);printf("\n");return;
}
运行结果如下:
以上就是与大家分享的全部内容啦,如果觉得对你有帮助,不妨点赞、收藏哦,当然如果有什么谬误,还请大家不吝赐教!谢谢观看!
快排C语言三种实现方法(大同小异)相关推荐
- Fibonacci数列C语言三种实现方法
Fibonacci数列的数学公式 列举:1,1, 2, 3, 5, 8, 13... 第三项等于第一项与第二项的和 运用数组求解 #include <stdio.h>int main (v ...
- 视频剪辑完成,应该如何给视频配音?三种配音方法快来学
对短视频来说声音非常重要,因此为视频配音是每一位做短视频的作者都应当掌握的一个技能,我们很多时候看一段视频停不下来,就是因为视频中的bgm或者配音很好听,让我们忍不住把一个视频反复刷很多遍.所以要想视 ...
- n的阶乘三种实现方法(C语言)
最近整理了曾经写的程序,把n的阶乘三种实现方法与小伙伴们分享,希望能给初学者一些帮助. 1.递归 #include <stdio.h> int Fact(int n); int main( ...
- c语言for循环打印九九乘法口诀的三种简单方法
c语言for循环打印九九乘法口诀的三种简单方法 由于在学习c语言,今天在复习巩固知识,练习代码的时候,简单的总结了三种for循环打印九九乘法口诀的方法,加深了自己的理解.代码注释和简单的思路已经注释在 ...
- c语言错误1004,excel宏运行时提示错误1004的三种解决方法
在使用excel宏功能的时候,一些网友会遇到excel宏运行不了,软件提示:"运行时错误1004,应用程序定义或对象定义错误"的问题,那么,excel宏运行时错误1004怎么办?幸 ...
- 冒泡法排序函数c语言,【C语言】冒泡法排序的三种实现方法
冒泡法的三种排序方法: 1.数组排序 #include//#includeint main() { int i; int j; int tmp; int arr[8] = { 1, 3, 5, 7, ...
- 数组的TopK的三种解决方法---Java
方法一:常规方法,先完全排序 此种方法就不多做解释了,就是使用快排,归并,堆排序等方法先将数组完全排序,然后再取topK,时间复杂度为O(NlogN).而且这种方法不适用于大数据量,小内存. 方法二: ...
- Topk问题的三种求解方法
Topk问题的三种求解方法 什么是Topk问题 方法一:堆排序法 方法二:把N个数建堆,取出前k个 方法三:建一个k个数的堆 什么是Topk问题 其实顾名思义,这个问题也就是在N个数中找出前k个最值. ...
- 用python解析xml的几种方法,Python_XML的三种解析方法
什么是XML? XML 指可扩展标记语言(eXtensible Markup Language). XML 被设计用来传输和存储数据. XML是一套定义语义标记的规则,这些标记将文档分成许多部件并对这 ...
最新文章
- java三角形创建子类_如何创建子类,以便参数属于Java中的子类类型
- 【Android Gradle 插件】ProductFlavor 配置 ( multiDexEnabled 配置 | multiDexKeepFile | multiDexKeepProguard )
- linux查看服务器设备信息命令dmidecode
- 【机器学习基础】Softmax与Sigmoid你还不知道存在这些联系?
- 1562: 比较大小(思维)
- 小数位数_圆周率的小数位是否包含了所有的数字组合?
- .net 从txt中读取行数据_【VBA项目】从指定文件中读取数据并绘制图表
- java web简单工厂模式_JAVA设计模式之工厂模式(简单工厂模式+工厂方法模式)
- 1177: 按要求排序(指针专题)_L2算法基础第10课 排序中
- PPT 去除排练计时
- mac下如何设置excel下拉表格
- 国美易卡RMAN客户端工具,国美易卡备份有效数据
- 使用Java语言编写一个五子棋UI界面并实现网络对战功能(非局域网)
- marked.js读取markdown文件,图片实现点击放大
- 56个JavaScript 实用工具函数助你提升开发效率!
- 浅谈垃圾渗滤液处理设计要点
- 微信小程序云开发路由模块真机调试报错
- JavaScript之undefined的加(+)、减(-)、乘(*)、除(/)和取模(%)运算
- linux-shell系列5-统计
- 无穷大 计算机语言,数值编程语言能区分“最大有限数”和“无穷大”吗?