使用qsort排序struct未达预期,求问题原因及解决方法
qsort排序自定义结构体数组不符合预期的问题分析
问题描述
尝试用qsort对自定义kort结构体数组排序,结果混乱不符合预期。期望按kuloer(3→4→5→6)分组,每组内按vaerdi从小到大排列,但当前输出完全偏离这个规则。
代码中的核心错误
1. qsort调用的元素大小参数错误
qsort的第三个参数是单个元素的字节大小,你传入了sizeof(int),但实际要排序的是kort结构体,正确参数应为sizeof(kort)。这个错误会导致qsort无法正确识别数组元素的边界,排序时乱读内存,直接引发输出混乱。
2. 比较函数的类型转换与逻辑错误
比较函数的两个参数是指向kort结构体的指针,但你强制转换成了int*,只读取了结构体第一个成员的内存值(甚至因元素大小错误读到其他无关内存),完全没按「先比kuloer,再比vaerdi」的期望逻辑处理。
修正后的代码
#include <stdio.h> #include <stdlib.h> int el_cmp(const void *ep1, const void *ep2); typedef struct kort { int kuloer; int vaerdi; } kort; int main(void){ int i; int k[] = {3, 4, 5, 6}; int v[] = {2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14}; kort kort[52]; for (i = 0; i < 52; i++){ kort[i].kuloer = k[i % 4]; kort[i].vaerdi = v[i % 13]; } // 修正元素大小参数 qsort(kort, 52, sizeof(kort), el_cmp); for (i = 0; i < 52; i++){ printf("Kort%d: %d %d\n", i + 1, kort[i].kuloer, kort[i].vaerdi); } return 0; } // 修正比较函数的类型转换与排序逻辑 int el_cmp(const void *ep1, const void *ep2){ // 转换为kort结构体指针 const kort *tp1 = (const kort*) ep1; const kort *tp2 = (const kort*) ep2; // 先比较kuloer,不同则直接返回差值 if (tp1->kuloer != tp2->kuloer) { return tp1->kuloer - tp2->kuloer; } // kuloer相同时,比较vaerdi return tp1->vaerdi - tp2->vaerdi; }
修正说明
qsort的第三个参数改为sizeof(kort),确保qsort能正确遍历每个结构体元素。- 比较函数中把
void*转换为const kort*,先对比kuloer,当kuloer相等时再对比vaerdi,完全匹配期望的排序规则。
内容的提问来源于stack exchange,提问作者Frederik Woloszynski
相关产品推荐
相关产品推荐

