前言;
我一直在思考今天要写什么类型的文章,看到之前写的冒泡排序的写法,不过冒牌排序的算法只能针对于整型,我们如果想要排序浮点型,字符型的数据呢?这个时候我突然想到了比冒泡排序还好用的一个库函数,就是我们今天的主角——qsort函数,下面不多废话,直接进入正文:
目录:
1.qsort函数
1.1.qsort函数是什么
1.2.如何使用qosrt函数
2.冒泡排序和qsort的代码比较
正文:
1.qsort函数
1.1qosrt函数是什么
qosort函数其实是一个基于快速排序算法(这个算法小编目前还没有学会,所以有句话说的好:活到老学到老)的一个库函数,它可以讲一串数快速的完成排序,这一点就和冒泡排序有点相似,不过它可是比冒泡排序好用很多,因为它仅仅通过几行代码便可以快速的将一串数完成排序,我感觉一些读者朋友已经迫不及待地想要使用qsort函数了,那下面小编就要展现它的用法喽!
1.2.如何使用qsort函数
1.2.1.一个好用的网站的分享
在讲qsort函数使用之前,小编先向各位推荐一个好用的网站:cplusplus网站,这个网站可以查询到我们平常使用到的库函数,我们如果想要搜索库函数,就使用老版的网站,这个可以提供搜索功能(小编一会就把旧版网站分享到这小节最后),如果您进入的是新版网站,那么我通过图片进行演示,来帮助大家更好的找到该网站
进到了最后一个图片就是找到了小编所说的旧版,我们通过上面的搜索框可以找到我们想要的库函数,下面小编就拿printf函数来举例子:
小编在图片里面对于如何运用网站做出了解释,我们平常遇到不会的库函数或者想要学习新的库函数的时候,可以进入这个网站进行搜索来学习,下面是这个网站(旧版)的地址,大家一定要好好的去使用:cplusplus.com - The C++ Resources Network
1.2.如何使用qsort函数
我们可以通过小编刚才介绍的网站来对此函数进行了解(大家一定要将那个网站保存下来),如下图所展示的:
我们可以通过上图很清晰的看出来qsort函数的头文件是stdlib.h,以及它的返回类型是void,这个时候很多读者朋友们就疑惑了,为什么返回类型是void?其实这个很好解释,因为qsort函数不仅仅可以处理整型的语句,它还可以处理浮点型,字符型等等的数据,用void可以接受更加广泛的类型,如果我们想要排序什么类型的,将它替换就好了,我们不多废话了,下面来对函数内部元素进行解释,我将会通过代码的方式来直接进行解释:
void qsort(void* base, //这里指的是想要排序数组的首地址(第一个元素的指针),所以一维数组的话这里放置数组名就好了
size_t num, //这里是显示数组有几个元素,可以通过sizeof / sizeof的形式来进行计算
size_t size, //每一个元素的大小,直接用sizeof(其中一个元素就好了)
int (*compar)(const void*, const void*) //这个的话我会在出一个代码进行解释,这里是类似冒泡排序的比较环节);
对于上述的解释我已经放到代码里面了,读者朋友们可以直接观看代码,下面我们来说一下这个代码的主体部分,就是最后的比较环节,这个是此库函数实现的主体,我们可以来看一下这个网站对于这个的介绍:
通过介绍,我们首先要知道最后一个部分其实是一个函数指针(这里不得不再次感慨知识是环环相扣的,前面刚讲了函数指针,这里就运用上了),所以我们可以自己定个名字来调用它,通过上面的表格,我们可以知道如果返回值大于0的话,二者就会交换,小于0或者等于0就不掉换了,所以我们可以通过两种形式来调用这个函数,下面先展示常规写法:
int com_per(const void* p1, const void* p2) //这里的话直接照搬就好,这个形式其实是固定的
{
int c = *(int*)p1 - *((int*)p2); //我们这里拿整型进行举例,(int*)的意思是强制类型转换成int*类型的指针,再进行解引用就好了,二者做差来比较大小
if (c > 0)
return 1; //这里返回的值是不固定的,只要是大于0的就好
else if (c < 0)
return -1; //这里也是不固定的
else
return 0;
}
上面便是常规写法,我们通过解引用操作和强制类型转换操作来对两个数大小进行比较,再通过if语句来辨别大小关系,可能很多读者朋友会觉得这么写稍微有点复杂,其实小编平常也不是这么写的,下面我们来展示此函数运用的第二种方法:
int com_per(const void* p1, const void* p2)
{
return *((int*)p1) - *((int*)p2); //这里直接把比较结果直接返回了,省去了比较,见笑了代码的数量
}
这一种方法十分的巧妙,直接把结果进行了返回,正如我代码所言,直接把比较的环节去掉了 ,小编推荐读者朋友们在以后使用这个函数的时候直接这么写就对了!下面我们来比较一下冒泡排序和qsort函数之间的代码量对于比较十个数。
2.冒泡排序和qsort代码的比较
冒泡排序:
int com_per(const void* p1, const void* p2)
{
return *((int*)p1) - *((int*)p2);
}
int main()
{
int arr[10] = { 0 };
int i = 0;
int sz = sizeof(arr) / sizeof(arr[0]);
for (i = 0; i < sz; i++)
{
scanf("%d", arr + i);
}
qsort(arr, sz, sizeof(arr[0]), com_per);
for (i = 0; i < sz; i++)
{
printf("%d ", arr[i]);
}
return 0;
}
void my_paopao(int arr[10], int sz)
{
int i = 0;
int tmp = 0;
int flag = 1;
for (i = 0; i < sz - 1; i++)
{
int j = 0;
for (j = 0; j < sz - i - 1; j++)
{
if (arr[j] > arr[j + 1])
{
tmp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = tmp;
flag = 0;
}
}
if (flag == 1)
break;
}
}
int main()
{
int arr[10] = { 0 };
int sz = sizeof(arr) / sizeof(arr[0]);
int i = 0;
for (i = 0; i < sz; i++)
{
scanf("%d", arr + i);
}
my_paopao(arr, sz);
for (i = 0; i < sz; i++)
{
printf("%d ", arr[i]);
}
}
很明显,冒泡排序的代码更长一点,qsort库函数的代码更短一点,可能很多读者朋友会这么想:那么我们为什么不直接去学qsort函数而去学冒泡排序呢?其实这么想是不对的,我们学习的并不是冒泡排序怎么打出来,而是学习它算法的思想,锻炼自己的逻辑思维,qosrt库函数固然好用,但这不会让我们懂它背后的逻辑(所以我准备下一篇模拟qsort函数,敬请期待),我们可以在平常的场景中应用他,但也不要忘记冒泡排序如何去写,我们要透过现象看本质 ,明白它背后的逻辑,懂得此代码为什么去写!我们不要过度依赖库函数,要有着自己的思想,如今很多人说现在是AI时代,AI时代会淘汰程序员这种话,我觉着这是错误的,因为AI终究是机器思想,它可能会帮我们去干一些活,虽然很好用,但也会让我们不在想思考,让我们思考能力下降,所以我们也是不能一直依赖AI,我们要会自己思考,况且程序员也是不断在学习的,目前程序员还是无法被淘汰的,这里说了不少脱离文章本身的话,也是通过滥用库函数而感慨一些了。
总结:
今天我们讲述了一个好用的库函数,qsort函数,各位要学会它的使用方法,并且一定不要忘记冒泡排序的代码实现,一定要透过现象去看本质!先来预告一下,小编下一节将会用冒泡排序来模拟实现qsort函数(本来想这篇写的,但我忘记怎么模拟实现了,我先学习一下怎么模拟实现),如果文章有错误,恳请在评论区指出,我一定虚心请教,那我们下一篇文章见喽!
标签:arr,初阶,函数,int,qsort,冒泡排序,库函数 From: https://blog.csdn.net/effort123_/article/details/139699424