C语言qsort函数的使用详解
文章目录
- 一、qsort函数简介
- 1.函数原型
- 2.参数含义
- 3.比较函数详解
- 二、比较函数使用案例
- 1.整型数组
- 2.字符数组
- 3.double型数组
- 4.字符串
- 1.按字符串首字母进行排序
- 2.按字符串长度进行排序
- 3.按字典进行排序
- 5.结构体
- 三、qsort函数完整使用案例
- 1.整型数组
- 2.字符数组
- 3.double型数组
- 4.字符串
- 1.按字符串首字母进行排序
- 2.按字符串长度进行排序
- 3.按字典进行排序
- 5.结构体
一、qsort函数简介
qsort()函数是C语言库函数中的一种排序算法,其用到的排序思想是快速排序(quicksort)。它的独特之处在于可以排序任意类型的数组元素(整形、浮点型、字符串和结构体类型)。
1.函数原型
void qsort ( void * base, size_t num, size_t size, int ( * comparator ) ( const void *, const void * ) );
2.参数含义
① void * base
:待排序数组的首地址。
②size_t num
:数组元素的个数。
③size_t size
:一个数组元素的大小(所占字节数)。
④int ( * comparator ) ( const void *, const void * ):
首先它是一个函数指针,指向的函数是排序函数;其此所包含的两个参数为所比较元素的地址;最后是参数类型为void*的原因是它的独特之处,可以接收任意类型的参数。
3.比较函数详解
以整形排序为例:
int cmp_int( const void * elem1, const void * elem2 )
{return *(int*)elem1-*(int*)elem2;
}
此函数为自定义函数(比较函数),函数的返回值类型为 int 类型,总共有三种情况:< 0:elem1小于elem2;0:elem1等于elem2;> 0:elem1大于elem2。
(const void * elem1, const void * elem2)
两个参数表示所要比较元素的地址,之所以参数的接收类型为 void* 是因为比较元素的类型是不清楚的,只能以 void* 这个万能桶进行接收;const表示指针所指向元素的值无法更改。`
return *(int*)elem1-*(int*)elem2;
对两个元素指针进行强制类型转化为整型指针,再进行解引用获取比较元素的值,最后将两个元素的差值返回。当然也可以根据比较元素的类型将其强制类型转化。
二、比较函数使用案例
1.整型数组
int cmp_int(const void* elem1, const void* elem2)
{return *(int*)elem1 - *(int*)elem2;
}
2.字符数组
int cmp_char(const void* elem1, const void* elem2)
{return *(char*)elem1 - *(char*)elem2;
}
3.double型数组
int cmp_double(const void* elem1, const void* elem2)
{return *(double*)elem1 > *(double*)elem2 ? 1 : -1;
}
注:此函数返回类型为 int 型,浮点型相减的数字会丢失小数点后的数字从而造成误差。若差值为大于零且小于一,则返回值会被设置为零。
4.字符串
1.按字符串首字母进行排序
int cmp_string(const void* elem1, const void* elem2)
{return *(char*)elem1 - *(char*)elem2;
}
2.按字符串长度进行排序
int cmp_string(const void* elem1, const void* elem2)
{ return strlen((char * )elem1) > strlen((char * )elem2) ? 1 : -1;
}
3.按字典进行排序
int cmp_string(const void* elem1, const void* elem2)
{return strcmp((char*)elem1,(char*)elem2);
}
5.结构体
struct Stu
{char name[10];int grade;
} s;
1.一级排序:对所有学生进行名字排序。
int cmp_name(const void* elem1, const void* elem2)
{return strcmp(((Stu*)elem1)->name, ((Stu*)elem2)->name);
}
2.二级排序:若名字相同则按照成绩再进行排序,若有三级排序,以此类推。
int cmp_s(const void* elem1, const void* elem2)
{if ((strcmp(((Stu*)elem1)->name, ((Stu*)elem2)->name))!=0)return strcmp(((Stu*)elem1)->name, ((Stu*)elem2)->name);elsereturn ((Stu*)elem1)->grade - ((Stu*)elem2)->grade;
}
三、qsort函数完整使用案例
1.整型数组
int cmp_int(const void* elem1, const void* elem2)
{return *(int*)elem1 - *(int*)elem2;
}
int main()
{int arr[10] = { 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);for (int i = 0; i < sz; i++){printf("%d ", arr[i]);}printf("\n");return 0;
}
2.字符数组
int cmp_char(const void* elem1, const void* elem2)
{return *(char*)elem1 - *(char*)elem2;
}
int main()
{char arr[] = { 'g', 'f', 'e', 'd', 'c', 'b', 'a' };int sz = sizeof(arr) / sizeof(arr[0]);qsort(arr, sz, sizeof(arr[0]), cmp_char);for (int i = 0; i < sz; i++){printf("%c ", arr[i]);}printf("\n");return 0;
}
3.double型数组
int cmp_double(const void* elem1, const void* elem2)
{return *(double*)elem1 > *(double*)elem2 ? 1 : -1;
}
int main()
{double arr[10] = { 5.32, 9.34, 1.27, 0.28, 0.98, 8.98, 5.69, 4.33, 7.01, 9.90 };int sz = sizeof(arr) / sizeof(arr[0]);qsort(arr, sz, sizeof(arr[0]), cmp_double);for (int i = 0; i < sz; i++){printf("%f ", arr[i]);}printf("\n");return 0;
}
4.字符串
1.按字符串首字母进行排序
int cmp_string(const void* elem1, const void* elem2)
{return *(char*)elem1 - *(char*)elem2;
}
int main()
{char arr[6][10] = { "grape", "face", "dog", "cat", "black", "apple" };int sz = sizeof(arr) / sizeof(arr[0]);qsort(arr, sz, sizeof(arr[0]), cmp_string);for (int i = 0; i < sz; i++){printf("%s ", arr[i]);}printf("\n");return 0;
}
2.按字符串长度进行排序
int cmp_string(const void* elem1, const void* elem2)
{ return strlen((char * )elem1) > strlen((char * )elem2) ? 1 : -1;
}
int main()
{char arr[6][10] = { "aaa", "aaaaa", "aaaaaaa", "aaaaaa", "aa", "aaaa" };int sz = sizeof(arr) / sizeof(arr[0]);qsort(arr, sz, sizeof(arr[0]), cmp_string);for (int i = 0; i < sz; i++){printf("%s ", arr[i]);}printf("\n");return 0;
}
3.按字典进行排序
int cmp_string(const void* elem1, const void* elem2)
{return strcmp((char*)elem1,(char*)elem2);
}
int main()
{char arr[6][10] = { "grrfdg","adew","gderfe","abrfggfe","lerf","lmnp" };int sz = sizeof(arr) / sizeof(arr[0]);qsort(arr, sz, sizeof(arr[0]), cmp_string);for (int i = 0; i < sz; i++){printf("%s ", arr[i]);}printf("\n");return 0;
}
5.结构体
一级排序与字符串的比较类似,直接看二级排序。
typedef struct Stu
{char name[10];int grade;
}Stu;
int cmp_s(const void* elem1, const void* elem2)
{if ((strcmp(((Stu*)elem1)->name, ((Stu*)elem2)->name))!=0)return strcmp(((Stu*)elem1)->name, ((Stu*)elem2)->name);elsereturn ((Stu*)elem1)->grade - ((Stu*)elem2)->grade;
}
int main()
{Stu s[] = { { "zhaoda", 89 }, { "qianer", 100 }, { "sunsan", 101 }, { "lisi", 121 }, { "sunsan", 95 }, {"zhaoda",78} };int sz = sizeof(s) / sizeof(s[0]);qsort(s, sz, sizeof(s[0]), cmp_s);for (int i = 0; i < sz; i++){printf("%s %d\n", s[i].name,s[i].grade);}return 0;
}
C语言qsort函数的使用详解相关推荐
- php函数find的用法,c语言find函数的用法详解
c语言find函数的用法详解 C语言之find()函数 find函数用于查找数组中的某一个指定元素的位置. 比如:有一个数组[0, 0, 5, 4, 4]: 问:元素5的在什么位置,find函数 返回 ...
- c语言memset函数用法,C语言memset函数使用方法详解
C语言memset函数使用方法详解 一.函数原形 void * memset(void*s, int ch,size_t n) 二.函数作用 将以s内存地址为首的连续n个字节的内容置成ch,一 ...
- c语言memset函数作用,C语言memset函数使用方法详解
C语言memset函数使用方法详解 一.函数原形 void * memset(void*s,int ch,size_t n) 二.函数作用 将以s内存地址为首的连续n个字节的内容置成ch,一般 ...
- C语言rand()函数产生随机数详解
C语言rand函数产生随机数详解 1.rand函数的原型,功能和界限 2.用rand函数获取随机数 3.随机数生成原理 1.rand函数的原型,功能和界限 rand函数的原型: #include &l ...
- 计算机科学类专升本复习之“C语言fopen函数的用法”详解(初稿)
C语言fopen函数的用法,C语言打开文件详解 在C语言中,"操作文件" 之前 必须 先"打开文件"; 所谓"打开文件",就是让 " ...
- c语言getline函数什么意思,详解C++ cin.getline函数
cin 虽然可以使用 cin 和 >> 运算符来输入字符串,但它可能会导致一些需要注意的问题. 当 cin 读取数据时,它会传递并忽略任何前导白色空格字符(空格.制表符或换行符).一旦它接 ...
- c语言的程序运行原理图,C语言main函数的原理详解
C语言标准在一开始(C90标准 5.1.2条),就规定了程序的执行环境.对于没有操作系统的环境来说,C程序的入口函数是什么都可以(也就是说的在单片机的C程序里,或者在操作系统的底层代码的C入口处,不需 ...
- c语言rand函数的作用,详解C语言中rand函数的使用
前言 我们在编程实现算法的过程中,往往需要使用到随机数.由于计算机是一台以逻辑为基础的机器,没法做到真正的随机(大概量子计算机可以?).所以计算机生成的是伪随机数,供我们使用. 我们使用C语言的ran ...
- 【C语言】函数递归(详解)
文章目录 函数递归 什么是递归? 递归的俩个必要条件 代码引例1 栈溢出(Stack Overflow) 合理使用递归 代码引例3 代码引例4 解释要合理使用递归 结束语 函数递归 程序调用自身的编程 ...
最新文章
- .NET英文技术文章导读(2017-02-09)
- 怎么学JavaScript?
- access后台链接mysql_ASP.NET连接 Access数据库的几种方法
- 分析了这么多年的福利彩票记录,原来可以用Python这么买彩票!
- ORACLE性能优化救生指南_21章 重做和归档的优化
- 使用叶神模拟器无法访问本机服务器的问题(报错:java.net.ConnectException: failed to connect to /127.0.0.1 (port 5000) )
- 为了治好你的脸盲,这家表情包网站开源了一个明星识别器丨GitHub
- Golang sort 排序
- 百亿级别数据量,又需要秒级响应的案例,需要什么系统支持呢?下面介绍下大数据实时分析工具Yonghong Z-Suite...
- 项目运行报‘vue-cli-service‘ 不是内部或外部命令,也不是可运行的程序 或批处理文件“
- MAC上Maven下载及安装
- CSS设置字间距、行间距、首行缩进
- 编译安装nginx实现反向代理、负载均衡、缓存功能
- 计算雅思成绩C语言,雅思成绩到底如何计算的?
- python电路仿真_蔡氏电路仿真实验
- iOS something is trying to start the receiver simultaneously from more than one thread
- H3C HCL MPLS 2层专线实验
- 2023.04.27 QT 制作文本编辑器
- 985高校大数据专业教学究竟怎么样?在校生有话说
- Android的GridView控件
热门文章
- 吉布斯现象( Gibbs)
- 给毕业4年的待业者——要将学习继续下去
- 《kafka 核心技术与实战》课程学习笔记(五)
- Python编程:为世界贡献你的轮子-pipy打包
- 软件测试基础篇五App之adb命令
- 第六章:Matplotlib之场景案例显神通
- mysql 列转行 unpivot_T-Sql语法:行转列(pivot)和列转行(unpivot)
- 冲压模具设计的方法与步骤
- pytest学习总结二:setup和teardown的使用总结
- error: ..\..\..\..\opencv\modules\highgui\src\window.cpp:261: error: (-215) size.width0 size.hei