博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
qsort函数
阅读量:4117 次
发布时间:2019-05-25

本文共 3337 字,大约阅读时间需要 11 分钟。



介绍qsort函数之前,我们先了解一下什么是回调函数??

回调函数就是⼀个通过函数指针调⽤的函数。如果你把函数的指针(地址)作为参数传递给另⼀个函数,当这个指针被⽤来调⽤其所指向的函数时,我们就说这是回调函数。回调函数不是由该函数的实现⽅直接调⽤,⽽是在特定的事件或条件发⽣时由另外的⼀⽅调⽤的,⽤于对该事件或条件进⾏响应。qsort函数就是根据回调函数实现的。

接下来介绍一下qsort函数

1.编译器函数库自带的快速排序函数。

2.使用qsort()排序并用 bsearch()搜索是一个比较常用的组合,使用方便快捷。

3.qsort 的函数原型是:void qsort(void*base, size_t num, size_t width, int(__cdecl*compare)(const void*, const void*));

各参数:1 待排序数组首地址 ;2 数组中待排序元素数量 ;3 各元素的占用空间大小; 4 指向函数的指针(待定函数的比较方法)

int(__cdecl*compare)()就是回调函数,将函数本身作为参数传递给对应的方法,然后在特定的时候再调用。

现在我们模仿qsort的功能实现一个通用的冒泡排序:

#include
#include
#include
//回调函数int int_cmp(const void *p1, const void *p2){ int *_p1 = (int *)p1; int *_p2 = (int *)p2; if (*_p1 < *_p2) { return 1;//降序 } else if (*_p1 > *_p2) { return -1; } else { return 0; }}//交换void swap(char *x, char *y, int width){ while (width--) { *x^=*y; *y^=*x; *x^=*y; x++; y++; }}//实现qsortvoid my_qsort(void *arr, int num, int width, int(*cmp)(void *, void *)){ assert(arr); assert(cmp); int i = 0; for (; i < num - 1; i++) { int j = 0; for (j = 0; j < num - 1 - i; j++) { //调用函数判断两个操作数大小。 //cmp()传参只需将操作数的地址传过去。 if (cmp((char *)arr + j*width, (char *)arr + (j + 1)*width)>0) //这里是任意类型,所以不能整体交换,只能局部按字节交换,达到整体交换的目的。 { swap((char *)arr + j*width, (char *)arr + (j + 1)*width, width); } } }}int main(){ int arr[] = { 1, 5, 4, 6, 8, 0, 9, 2, 7, 3 }; int size = sizeof(arr) / sizeof(arr[0]); int i = 0; my_qsort(arr, size, sizeof(int), int_cmp); for (i = 0; i < size; i++) { printf("%d\n", arr[i]);//9876543210 } system("pause"); return 0;}

通过上面模拟实现我们了解到qsort能够进行排序,接下来我们来练习使用qsort函数排序各种类型的数据。

1.int 类型:int int_cmp(const void *p1, const void *p2){	int *_p1 = (int *)p1;	int *_p2 = (int *)p2;	if (*_p1 < *_p2)	{		return 1;//降序	}	else if (*_p1 > *_p2)	{		return -1;	}	else	{		return 0;	}}int main(){	int arr[] = { 1, 5, 4, 6, 8, 0, 9, 2, 7, 3 };	int size = sizeof(arr) / sizeof(arr[0]);	int i = 0;	qsort(arr, size, sizeof(int), int_cmp);	for (i = 0; i < size; i++)	{		printf("%d\n", arr[i]);//9876543210	}	system("pause");	return 0;}

//2.double类型:int double_cmp(const void *p1, const void *p2){	double *_p1 = (double *)p1;	double *_p2 = (double *)p2;	if (*_p1 < *_p2)	{		return -1;//升序	}	else if (*_p1 > *_p2)	{		return 1;	}	else	{		return 0;	}}int main(){	double arr[] = { 10.3, 5.0, 4.345, 6.66, 8.9, 0.1, 9.4, 2.5, 7.35, 3.09 };	int size = sizeof(arr) / sizeof(arr[0]);	int i = 0;	qsort(arr, size, sizeof(double), double_cmp);	for (i = 0; i < size; i++)	{		printf("%f  ", arr[i]);	}//0.100000  2.500000  3.090000  4.345000  5.000000  6.660000  7.350000  8.900000 9.400000  10.300000  请按任意键继续. . .	system("pause");	return 0;}

//3.排序字符char类型:int char_cmp(const void *p1, const void *p2){	char *_p1 = (char *)p1;	char *_p2 = (char *)p2;	if (*_p1 < *_p2)	{		return -1;//升序	}	else if (*_p1 > *_p2)	{		return 1;	}	else	{		return 0;	}}int main(){	char arr[] = { 'v','A','g','t','H','M','d' };	int size = sizeof(arr) / sizeof(arr[0]);	int i = 0;	qsort(arr, size, sizeof(char), char_cmp);	for (i = 0; i < size; i++)	{		printf("%c  ", arr[i]);	}	//A  H  M  d  g  t  v  请按任意键继续. . .	system("pause");	return 0;}

注意字符串传参问题: 因为char*是字符数组,后面跟的相当于字符数组名,而指向字符数组(字符串)的指针,那就再加一星号,char**就是指向字符数组的指针了(当然它也可以表示字符串数组)。函数定义时使用char **s1和char **s2作参数,函数内容不需要变。

使用这两个形参后,在函数体中,*s1表示指针s1指向的字符数组(字符串),*s2表示指针s2指向的字符数组(字符串),因此,函数体不需要做改变。

 

转载地址:http://vmypi.baihongyu.com/

你可能感兴趣的文章
python 变量作用域问题(经典坑)
查看>>
pytorch
查看>>
pytorch(二)
查看>>
pytorch(三)
查看>>
pytorch(四)
查看>>
pytorch(5)
查看>>
pytorch(6)
查看>>
ubuntu相关
查看>>
C++ 调用json
查看>>
nano中设置脚本开机自启动
查看>>
动态库调动态库
查看>>
Kubernetes集群搭建之CNI-Flanneld部署篇
查看>>
k8s web终端连接工具
查看>>
手绘VS码绘(一):静态图绘制(码绘使用P5.js)
查看>>
手绘VS码绘(二):动态图绘制(码绘使用Processing)
查看>>
基于P5.js的“绘画系统”
查看>>
《达芬奇的人生密码》观后感
查看>>
论文翻译:《一个包容性设计的具体例子:聋人导向可访问性》
查看>>
基于“分形”编写的交互应用
查看>>
《融入动画技术的交互应用》主题博文推荐
查看>>