需要帮助使用 qsort 对 C 中的结构数组进行排序
Need help sorting an array of structures in C using qsort
我有这个结构。
struct Transport
{
int id;
float Price;
};
在这里我将数据读入结构数组。
void read (struct Transport **Car, int *m)
{
int i;
printf("Insert total number of cars: ");
scanf("%d",m);
*Car=(struct Transport*) malloc ((*m)*3*sizeof(struct Transport));
for(i=1; i<=*m; i++)
{
(*Car)[i].id=i;
printf("Price: ");
scanf("%f",&(*Car)[i].Price);
printf("\n");
}
}
这里是显示功能。
void display(struct Transport *Car,int m)
{
int i;
for(i=1; i<=m; i++)
{
printf("Entry #%d: \n",i);
printf("Price: %2.2f\n",(Car+i)->Price);
printf("\n");
}
}
现在 problem.I 必须按价格字段对数据进行排序。到目前为止,我已经试过了,但它什么也没做。
int struct_cmp_by_price(const void *a, const void *b)
{
struct Transport *ia = (struct Transport *)a;
struct Transport *ib = (struct Transport *)b;
return (int)(100.f*ia->Price - 100.f*ib->Price);
}
这是主要的样子。
int main()
{
int m;
struct Transport *Car;
read(&Car,&m);
qsort(Car, m, sizeof(struct Transport), struct_cmp_by_price);
display(Car,m);
return 0;
}
谁能帮帮我?
您的代码中存在多个问题:
你在read()
中分配了太多的内存,你不需要在C中转换malloc()
的return值,但你应该检查分配失败。你应该改用:
*Car = calloc(*m, sizeof(struct Transport));
if (*Car == NULL) {
fprintf(stderr, "cannot allocate memory for %d structures\n", *m);
exit(1);
}
您不应使用 read
作为函数名,因为它是系统调用的名称,可能与该函数的标准库使用冲突。使用 readTransport
.
索引是 0
基于 C 的。而不是 for(i=1; i<=*m; i++)
,使用:
for (i = 0; i < *m; i++)
比较函数不能使用减法技巧。事实上,减法技巧只能用于整数类型比int
小。改用这个:
int struct_cmp_by_price(const void *a, const void *b) {
const struct Transport *ia = a;
const struct Transport *ib = b;
return (ia->Price > ib->Price) - (ia->Price < ib->Price);
}
您应该测试 scanf()
的 return 值以检测无效输入。 Price
成员在转换失败的情况下保持未初始化,这会导致未定义的行为,除非您使用 calloc()
,但结果仍然没有意义。
您也可以尝试使用两个单独的结构体,使指针操作更容易处理。
这样的事情给出了正确的想法:
#include <stdio.h>
#include <stdlib.h>
typedef struct {
int id;
float price;
} transport_t;
typedef struct {
transport_t *Cars;
int numcars;
} Cars_t;
Cars_t *initialize_struct(void);
void read(Cars_t *Car);
void display(Cars_t *Car);
int price_cmp(const void *x, const void *y);
int
main(void) {
Cars_t *Car;
Car = initialize_struct();
read(Car);
printf("Before:\n");
display(Car);
qsort(Car->Cars, Car->numcars, sizeof(transport_t), price_cmp);
printf("\nAfter:\n");
display(Car);
free(Car->Cars);
free(Car);
return 0;
}
void
read(Cars_t *Car) {
int i, count = 0;
printf("Insert total number of cars: ");
if (scanf("%d", &(Car->numcars)) != 1) {
printf("Invalid entry\n");
exit(EXIT_FAILURE);
}
Car->Cars = calloc(Car->numcars, sizeof(transport_t));
if (Car->Cars == NULL) {
fprintf(stderr, "Issue allocating memory for %d members", Car->numcars);
exit(EXIT_FAILURE);
}
for (i = 1; i <= Car->numcars; i++) {
Car->Cars[count].id = i;
printf("Car id %d\n", Car->Cars[count].id);
printf("Price: ");
scanf("%f", &(Car->Cars[count].price));
count++;
printf("\n");
}
}
void
display(Cars_t *Car) {
int i;
for (i = 0; i < Car->numcars; i++) {
printf("Car id: %d, Car price: %2.2f\n",
Car->Cars[i].id, Car->Cars[i].price);
}
}
Cars_t
*initialize_struct(void) {
Cars_t *Car;
Car = malloc(sizeof(*Car));
if (Car == NULL) {
fprintf(stderr, "%s", "Issue allocating memory for structure");
exit(EXIT_FAILURE);
}
Car->Cars = NULL;
Car->numcars = 0;
return Car;
}
int
price_cmp(const void *x, const void *y) {
const transport_t *car1 = x;
const transport_t *car2 = y;
if (car1->price > car2->price) {
return +1;
} else if (car1->price < car2->price) {
return -1;
}
return 0;
}
我有这个结构。
struct Transport
{
int id;
float Price;
};
在这里我将数据读入结构数组。
void read (struct Transport **Car, int *m)
{
int i;
printf("Insert total number of cars: ");
scanf("%d",m);
*Car=(struct Transport*) malloc ((*m)*3*sizeof(struct Transport));
for(i=1; i<=*m; i++)
{
(*Car)[i].id=i;
printf("Price: ");
scanf("%f",&(*Car)[i].Price);
printf("\n");
}
}
这里是显示功能。
void display(struct Transport *Car,int m)
{
int i;
for(i=1; i<=m; i++)
{
printf("Entry #%d: \n",i);
printf("Price: %2.2f\n",(Car+i)->Price);
printf("\n");
}
}
现在 problem.I 必须按价格字段对数据进行排序。到目前为止,我已经试过了,但它什么也没做。
int struct_cmp_by_price(const void *a, const void *b)
{
struct Transport *ia = (struct Transport *)a;
struct Transport *ib = (struct Transport *)b;
return (int)(100.f*ia->Price - 100.f*ib->Price);
}
这是主要的样子。
int main()
{
int m;
struct Transport *Car;
read(&Car,&m);
qsort(Car, m, sizeof(struct Transport), struct_cmp_by_price);
display(Car,m);
return 0;
}
谁能帮帮我?
您的代码中存在多个问题:
你在
read()
中分配了太多的内存,你不需要在C中转换malloc()
的return值,但你应该检查分配失败。你应该改用:*Car = calloc(*m, sizeof(struct Transport)); if (*Car == NULL) { fprintf(stderr, "cannot allocate memory for %d structures\n", *m); exit(1); }
您不应使用
read
作为函数名,因为它是系统调用的名称,可能与该函数的标准库使用冲突。使用readTransport
.索引是
0
基于 C 的。而不是for(i=1; i<=*m; i++)
,使用:for (i = 0; i < *m; i++)
比较函数不能使用减法技巧。事实上,减法技巧只能用于整数类型比
int
小。改用这个:int struct_cmp_by_price(const void *a, const void *b) { const struct Transport *ia = a; const struct Transport *ib = b; return (ia->Price > ib->Price) - (ia->Price < ib->Price); }
您应该测试
scanf()
的 return 值以检测无效输入。Price
成员在转换失败的情况下保持未初始化,这会导致未定义的行为,除非您使用calloc()
,但结果仍然没有意义。
您也可以尝试使用两个单独的结构体,使指针操作更容易处理。
这样的事情给出了正确的想法:
#include <stdio.h>
#include <stdlib.h>
typedef struct {
int id;
float price;
} transport_t;
typedef struct {
transport_t *Cars;
int numcars;
} Cars_t;
Cars_t *initialize_struct(void);
void read(Cars_t *Car);
void display(Cars_t *Car);
int price_cmp(const void *x, const void *y);
int
main(void) {
Cars_t *Car;
Car = initialize_struct();
read(Car);
printf("Before:\n");
display(Car);
qsort(Car->Cars, Car->numcars, sizeof(transport_t), price_cmp);
printf("\nAfter:\n");
display(Car);
free(Car->Cars);
free(Car);
return 0;
}
void
read(Cars_t *Car) {
int i, count = 0;
printf("Insert total number of cars: ");
if (scanf("%d", &(Car->numcars)) != 1) {
printf("Invalid entry\n");
exit(EXIT_FAILURE);
}
Car->Cars = calloc(Car->numcars, sizeof(transport_t));
if (Car->Cars == NULL) {
fprintf(stderr, "Issue allocating memory for %d members", Car->numcars);
exit(EXIT_FAILURE);
}
for (i = 1; i <= Car->numcars; i++) {
Car->Cars[count].id = i;
printf("Car id %d\n", Car->Cars[count].id);
printf("Price: ");
scanf("%f", &(Car->Cars[count].price));
count++;
printf("\n");
}
}
void
display(Cars_t *Car) {
int i;
for (i = 0; i < Car->numcars; i++) {
printf("Car id: %d, Car price: %2.2f\n",
Car->Cars[i].id, Car->Cars[i].price);
}
}
Cars_t
*initialize_struct(void) {
Cars_t *Car;
Car = malloc(sizeof(*Car));
if (Car == NULL) {
fprintf(stderr, "%s", "Issue allocating memory for structure");
exit(EXIT_FAILURE);
}
Car->Cars = NULL;
Car->numcars = 0;
return Car;
}
int
price_cmp(const void *x, const void *y) {
const transport_t *car1 = x;
const transport_t *car2 = y;
if (car1->price > car2->price) {
return +1;
} else if (car1->price < car2->price) {
return -1;
}
return 0;
}