C语言--qsort函数理解

说明: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函数排序原理掌握之后可以快速排序任何类型数据,将它的原理进行延伸可以很好的提高我们的编程思维。

点点关注,点点赞,就是对小编最大的支持呢!

欢迎各位指出小编不足之处,我们共同进步!

  • 7
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值