说明:qsort是c语言中的一个库函数,它是基于快速排序算法的一个排序函数,它相比其他函数的优点是能够排序任意类型的数据。
注意:qsort的使用必须包含#include<stdlib.h>
首先它的结构如下:
qsort(void base ,//指针,指向的是待排序的数组的第一个元素地址
size_t num,//是base指向的待排序数组的元素个数
size_t size,//是base指向的待排序数组的元素大小
int (*compar)(const void*,const void*)); 函数指针,指向的就是两个元素的比较元素
其中void*为无符号类型,必须强制类型转化
实际运用如下:
1:qsort排序整型数组
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<stdlib.h>
int cmp_int(const void* p1, const void* p2)
{
/* if (*(int*)p1 > *(int*)p2)
return 1;
else if (*(int*)p1 > *(int*)p2)
return 0;
else
return -1;*/
return *(int*)p1 - *(int*)p2;
}
void test1()
{
int arr[] = { 9,8,7,6,5,4,3,2,1,0 };
int sz = sizeof(arr) / sizeof(arr[0]);
qsort(arr, sz, sizeof(arr[0]), cmp_int);
print(arr, sz);
}
这个函数过程是通过qsort函数快速进行排序,依次传入数组首元素地址,数组元素个数,元素大小,调用cmp_int. 然后通过cmp_int()函数每次传入两个地址进行比较,然后因为void*为无符号类型所以必须强制类型转化成(int*)才能进行整型元素之间的比较。*(int*)p1 - *(int*)p2是指两个元素相减当*p1>*p2时结果>0它就会返回正数qsort函数就会将这两个元素交换,当*p1<*p2时或者*p1=*p2时会返回<0和0这时qsort函数就不会将这两个元素交换。
延伸--冒泡排序整型数组:
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
int bubble_sort(int arr[], int sz)
{
for (int i = 0; i < sz-1; i++)//趟数
{
for (int j = 0; j < sz - 1 - i; j++)
{
if (arr[j] > arr[j + 1])
{
int temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
}
}
void print(int arr[], int sz)
{
int i = 0;
for (i = 0; i < sz; i++)
{
printf("%d ", arr[i]);
}
}
int main()
{
int arr[] = { 9,8,7,6,5,4,3,2,1,0 };
int sz = sizeof(arr) / sizeof(arr[0]);
bubble_sort(arr, sz);
print(arr, sz);
return 0;
}
相较于冒泡排序,qsort优势有思路简单,排序快等特点。
2:qsort排序结构体
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
struct Stu
{
char name[20];
int age;
};
//这里的两个结构体元素怎么比较?
//1:按照年龄进行比较-整型比较
//2:按照名字比较-字符串类型比较
int cmp_stu_by_age(const void* p1, const void* p2)
{
//return strcmp(((struct Stu*)p1)->name, ((struct Stu*)p2)->name);
return ((struct Stu*)p1)->age - ((struct Stu*)p2)->age;
}
void test2()
{
struct Stu arr[3] = { {"zhangsan",20},{"lisi",35},{"wangwu",18} };
int sz = sizeof(arr) / sizeof(arr[0]);
qsort(arr, sz, sizeof(arr[0]), cmp_stu_by_age);
}
int main()
{
test2();
return 0;
}
这里我们可以通过创建结构体变量name,age 来这里我们就可以通过qsort函数来比较这两个函数,与上面同理,不过需要注意的是strcmp(((struct Stu*)p1)->name, ((struct Stu*)p2)->name)这里的strcmp是用来比较两个字符串的ASCII值的当p1>p2时返回正数,p1<p2时返回负数,p1=p2时返回0.
同样大家可以想想如何通过改变冒泡排序来进行结构体的排序呢?
延伸--冒泡排序结构体
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<string.h>
struct Stu
{
char name[20];
int age;
};
int cmp_stu_by_age(const void* p1, const void* p2)
{
return strcmp(((struct Stu*)p1)->name, ((struct Stu*)p2)->name);
//return ((struct Stu*)p1)->age - ((struct Stu*)p2)->age;
}
void Swap(char* buf1, char* buf2, size_t width)
{
int i = 0;
for( i = 0;i < width; i++)
{
char tmp =*buf1;
*buf1 = *buf2;
*buf2 = tmp;
buf1++;
buf2++;
}
}
int bubble_sort(void* base, size_t sz,size_t width,int(*cmp)(const void* p1,const void* p2))
{
for (int i = 0; i < sz-1; i++)//趟数
{
for (int j = 0; j < sz - 1 - i; j++)
{
if (cmp((char*)base + j * width, (char*)base + (j + 1) * width)>0)
{
Swap((char*)base + j * width, (char*)base + (j + 1) * width, width);
}
}
}
}
void test3()
{
struct Stu arr[3] = { {"zhangsan",20},{"lisi",35},{"wangwu",18} };
int sz = sizeof(arr) / sizeof(arr[0]);
qsort(arr, sz, sizeof(arr[0]), cmp_stu_by_name);
}
int main()
{
test3();
return 0;
}
总结:qsort函数排序原理掌握之后可以快速排序任何类型数据,将它的原理进行延伸可以很好的提高我们的编程思维。
点点关注,点点赞,就是对小编最大的支持呢!
欢迎各位指出小编不足之处,我们共同进步!