简体   繁体   English

使用qsort函数在C中对结构数组进行排序

[英]Sorting an struct array in C with qsort function

First of all, I saw some examples like: 首先,我看到了一些示例,例如:

But they don't work for me. 但是他们对我不起作用。

My struct is 我的结构是

typedef struct Team {
    int total;
    char name[N][N];   // Nombre
    int points[N];     // Points
    int pg[N];         // Won Matches
    int pe[N];         // Tied Matches
    int pp[N];         // Lost Matches
    int gf[N];         // Goals For 
    int gc[N];         // Goals Against
} Teams;

int compareTeams(struct Team *e1, struct Team *e2){
    int comparer;
    int dg1 = e1->gf - e1->gc;
    int dg2 = e2->gf - e2->gc;

    //classified according to the points
    if (e1->points > e2->points) {
        comparer=-1;
    } else if (e1->points < e2->points) {
        comparer=1;
    } else {
        // with the same points, goal difference check
        if (dg1 > dg2) {
            comparer=-1;
        } else if (dg1 < dg2) {
            comparer=1;
        } else {
            // with the same goal difference , we check who scored more goals
            if(e1->gf > e2->gf) {
                comparer=-1;
            } else if (e1->gf < e2->gf) {
                comparer=1;
            } else
                comparer=0;
        }
    }
    return comparer;
}

In main function, I have this: 在主要功能中,我有这个:

Teams teams[100];
qsort(teams, teams->total, sizeof(struct Team), &compareTeams);

But obviously, it doesn't work :( 但显然,它不起作用:(

You have a single struct: 您只有一个结构:

typedef struct Team {
    int total;
    char name[N][N];   // Nombre
    int points[N];     // Points
    int pg[N];         // Won Matches
    int pe[N];         // Tied Matches
    int pp[N];         // Lost Matches
    int gf[N];         // Goals For 
    int gc[N];         // Goals Against
} Teams;

This struct is misnamed; 该结构的名称不正确; it is not a team, it is a league. 它不是团队,而是联盟。 All fields except total are themselves arrays. total以外的所有字段本身都是数组。 If you want to sort this struct, you would have to swap all arrays simultaneously, because they are essentially independent. 如果要对该结构进行排序,则必须同时交换所有数组,因为它们本质上是独立的。 qsort can't do that; qsort无法做到这一点; you would have to write your own sorting algorithm. 您将必须编写自己的排序算法。

It makes managing the teams and also sorting easier when you restructure your data: A team should only contain the data for itself: 当您重组数据时,它使团队的管理和排序更加容易:团队应只包含自身的数据:

typedef struct Team {
    char name[24];
    int points;               // Points
    int won, drawn, lost;     // Match records
    int scored, conceded;     // Goal records
} Teams;

Then you can create an array of teams: 然后,您可以创建一组团队:

Team league[] = {
    {"FC Bayern Muenchen",   85,   27,  4,  2,   77, 16},
    {"Borussia Dortmubd",    77,   24,  5,  4,   80, 32},
    {"Bayer 04 Leverkusen",  57,   17,  6, 10,   53, 38},
    {"Borussia M'Gladbach",  52,   16,  4, 13,   65, 50},
    // ...
};

Then write a comparison function to obeys the definition used in qsort : 然后编写一个比较函数来遵循qsort使用的定义:

int compareTeams(const void *p1, const void *p2)
{
    const Team *e1 = p1;
    const Team *e2 = p2;

    int dg1 = e1->gf - e1->gc;
    int dg2 = e2->gf - e2->gc;

    if (e1->points > e2->points) return -1;
    if (e1->points < e2->points) return 1;

    if (dg1 > dg2) return -1;
    if (dg1 < dg2) return 1;

    if (e1->gf > e2->gf) return -1;
    if (e1->gf < e2->gf) return 1;

    return 0;
}

and use it: 并使用它:

qsort(league,
    sizeof(league) / sizeof(*league),    // number of teams
    sizeof(*league),                     // size of one team
    compareTeams);

The restructuring means that the data for each team is kept together in the same struct and instead of swapping many independent arrays in order to keep them in sync, you swap whole teams. 重组意味着将每个团队的数据保存在同一结构中,而不是交换许多独立的数组以保持同步,而是交换整个团队。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM