首先,我们先将这个原函数找出来,对每个参数部分进行实现
那我们自己写的这个bubble_sort函数的各个参数至少都得一样,这是保持函数功能一样的最低标准(除了有的参数名称不同)
实际上,这个函数的内部原理依旧是冒泡法的原理
难点就是内部进行arr[j]和arr[j+1]的比较,并且升序排序
我们现在知道需要比较数据元素的首原素的地址,知道每个元素所占的字节大小,数据元素数量,和compar函数的返回类型,我们要每次精确定位每一个数据元素,就必须与 j 相结合,我们可以先将base强制类型转化为char*类型,char*类型只占一个字节,那么当你用j去乘、数据元素的字节数再加上数据元素本身的地址时,就可以精确锁定arr[j]和arr[j+1]对应的元素
对应arr[j]
对应arr[j+1]
那么只需要知道compar函数的返回值,即可判断arr[j]和arr[j+1]的大小,并判断是否交换,即
再写交换函数,由于我们不知道我们要排序的到底是什么类型的数据类型,可能是int.可能是float还可能是char,结构体等等,所以难点依旧是再比较完两个数据类型后,如何交换它。因为我们之前已经将要比较数据元素的地址类型强制转化为(char*)类型,所以每次指针加一只向前移动一个字节,并且要交换的两个数据元素的类型肯定是相同的,所以可以每次只交换一个字节的内容
这样就可以将两个数据元素交换,至于要进行什么数据元素类型的排序,则可以又自己来定,对应的compar函数也需要自己来写,我这里就用int型来举例子
#include<stdio.h> //自己实现qsort函数 //void qsort (void* base, size_t num, size_t size,int (*compar)(const void*, const void*)); void swap(char* buff1, char* buff2,int width) { int i = 0; for (i = 0; i <width; i++) { char tmp = *buff1; *buff1 = *buff2; *buff2 = tmp; buff1++; buff2++; } } void bubble_sort(void* base, int num, int width, int(*compar)(const void*, const void*)) { int i = 0; for (i = 0; i < num - 1; i++) { int j = 0; for (j = 0; j < num - 1 - i; j++)// { //arr[j] arr[j+1]的实现 if (compar((char*)base + j * width , (char*)base + (j + 1) * width) > 0) { swap((char*)base + j * width, (char*)base + (j + 1) * width,width); } } } } int compar(const void* p1, const void* p2) { return (*(int*)p1) - (*(int*)p2); } int main() { int arr[10] = { 9,8,7,6,5,4,3,2,1,0 }; bubble_sort(arr,10,sizeof(arr[0]),compar);//自己的qsort函数 int i = 0; for (i = 0; i < 10; i++) { printf("%d ", arr[i]); } return 0; }
输出结果
成功!!!