qsort的使用练习以及模拟实现

qsort的使用练习以及模拟实现



什么是qsotr?

qsort是排序函数,在MSDN中显示Performs a quick sort.,即执行快速排序,
具体为
void qsort( void *base, size_t num, size_t width, int (__cdecl *compare )(const void *elem1, const void *elem2 ) );

void *base              目标矩阵的开始
size_t num              元素中的数组大小
size_t width              元素大小(以字节为单位)
int (__cdecl *compare )(const void *elem1, const void *elem2 ) 比较函数

在这里插入图片描述


qsort的使用

使用函数就需要传参,根据上述描述我们可以清楚的知道传参的值,这里值得注意的是比较函数。
void qsort( void *base, size_t num, size_t width, int (__cdecl *compare )(const void *elem1, const void *elem2 ) );
qsort函数传参类型多为void*,这就意味着我们可以对不同的数据类型按给定的规则排序。
比较函数就给定了排序规则
在这里插入图片描述
我们又知道,void这种类型不能加减乘数解应用,使用目的主要是为了可以排序多种数据类型,所以我们要利用好强制类型转换。

#include<stdio.h>
#include<stdlib.h>
int compare(void* elem1,void*elem2){
return *((int*)elem1) - *((int*)elem2);
}
int main(){
int arr[] = { 0, 5, 8, 4, 3, 1, 6, 9, 2, 7 };
int sz = sizeof(arr)/sizeof(arr[0]);
qsort(arr,sz,sizeof(int),compare);
int i = 0;
for (i = 0; i < sz; i++){
printf("%d ",arr[i]);
}
return 0;
}

运行结果:

在这里插入图片描述

qsort的模拟实现

qsort的模拟实现首先如何排序?怎么样解决不确定数据类型的排序?按何规则排序?
既然如此我们要知道数据从哪里开始到哪里结束,元素个数,元素每字节大小,还要比较函数

主函数部分:
主要是传参问题,参数需要
void *base              目标矩阵的开始
size_t num              元素中的数组大小
size_t width              元素大小(以字节为单位)
int (__cdecl *compare )(const void *elem1, const void *elem2 ) 比较函数

int main(){
	int arr[] = { 0, 5, 8, 4, 3, 1, 6, 9, 2, 7 };
	int sz = sizeof(arr) / sizeof(arr[0]);
	//qsort(arr, sz, sizeof(int), compare);
	my_qsort(arr, sz, sizeof(int), compare);
	//void qsort(void *base,     size_t num, size_t width, int(__cdecl *compare)(const void *elem1, const void *elem2));
	int i = 0;
	for (i = 0; i < sz; i++){
		printf("%d ", arr[i]);
	}
	return 0;
}

my_qsort函数部分:

既然数据类型是未知的,那我们只能用void*来完成传参,
这里使用冒泡排序,我们根据以上了解通过比较函数就知道如何排序,我们当比较函数大于0时就交换,完成排序
这里有个很严重的问题,我们不知道元素类型,我们怎么知道下一个元素是第几个字节开始的?
(char*)我们知道只可操作一个字节字符,只需要我们传的字符宽度就好。

void my_qsort(void* str, int num, int width, int compare(const void*(elem1), const void*(elem2))){
	int i = 0, j = 0;
	for (i = 0; i < num - 1; i++){
		for (j = 0; j < num - i - 1; j++){
			if (compare((char*)str + j*width, (char*)str + (j + 1) * width)>0){
				swap(str, num, width,j );
			}
		}
	}
}

交换代码:

当元素和后一个比较后大便交换位置,冒泡排序思想,不详细赘述。

void swap(void* str, int num, int width,int j){
	
				char tmp = *((char*)str + j * width);
				*((char*)str + j* width) = *((char*)str + (j + 1) * width);
				*((char*)str + (j + 1) * width) = tmp;
}

比较函数

int compare(void* elem1, void*elem2){
	return *((int*)elem1) - *((int*)elem2);
}

整体代码

#include<stdio.h>
#include<stdlib.h>
//用冒牌排序模拟实现qsort
//

int compare(void* elem1, void*elem2){
	return *((int*)elem1) - *((int*)elem2);
}
void swap(void* str, int num, int width,int j){
	
				char tmp = *((char*)str + j * width);
				*((char*)str + j* width) = *((char*)str + (j + 1) * width);
				*((char*)str + (j + 1) * width) = tmp;
}
void my_qsort(void* str, int num, int width, int compare(const void*(elem1), const void*(elem2))){
	int i = 0, j = 0;
	for (i = 0; i < num - 1; i++){
		for (j = 0; j < num - i - 1; j++){
			if (compare((char*)str + j*width, (char*)str + (j + 1) * width)>0){
				swap(str, num, width,j );
			}
		}
	}
}
int main(){
	int arr[] = { 0, 5, 8, 4, 3, 1, 6, 9, 2, 7 };
	int sz = sizeof(arr) / sizeof(arr[0]);
	//qsort(arr, sz, sizeof(int), compare);
	my_qsort(arr, sz, sizeof(int), compare);
	//void qsort(void *base,     size_t num, size_t width, int(__cdecl *compare)(const void *elem1, const void *elem2));
	int i = 0;
	for (i = 0; i < sz; i++){
		printf("%d ", arr[i]);
	}
	return 0;
}

运行结果:

在这里插入图片描述

总结

我这里似乎有一些bug,(char*)str+j*width,如果j = 0,如果是整数大于char能接受值范围之外将会出现bug,这怎么办呢?且听下回分解;

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值