Сортировка массива с помощью qsort () - PullRequest
0 голосов
/ 23 декабря 2018

Я пытаюсь проверить, содержат ли два массива одинаковые элементы.Поскольку я не знаю, правильно ли отсортирован входной файл, я хочу сначала использовать qsort() для сортировки массива, а затем сравнить его с массивом cmpvalues.

Однако я не могу получить qsort сортировать массив как массив cmpvalues.Массив, в котором хранятся значения, должен быть отсортирован так же, как массив cmpvalues, чтобы его было легче сравнивать.

#include <stdio.h>

#define MAXCOLR   14
#define MAXLINE  100
#define MAXCHR  1024   
#define _GNU_SOURCE

typedef struct {
    char color[MAXCOLR];
    int value;
} colorval_t;

int cmpfunc(const void *a, const void *b) {
    int aa, bb;
    aa = *(int *)a;
    bb = *(int *)b; 
    return (aa - bb);   
}

int main(int argc, char **argv) {
    size_t n;
    int cmpvalues[] = {
        65,
         2,
         3,
         4,
         5,
         6,
         7,
         8,
         9,
        10,
        74,
        81,
        75,
        65,
         2,
         3,
         4,
         5,
         6,
         7,
         8,
         9,
        10,
        74,
        81,
        75
    };
    size_t ndx = 0;
    char buf[MAXCHR];
    colorval_t arr[MAXLINE] = {{ .color = "" }};

    FILE *fp = argc > 1 ? fopen(argv[1], "r") : stdin;

    if (!fp) { 
        perror("file open failed");
        return 1;
    }

    while (ndx < MAXLINE && fgets(buf, MAXCHR, fp)) {
        char c;
        if (sscanf(buf, "%13s %d", arr[ndx].color, &arr[ndx].value) == 2)
            ndx++;
        else if (sscanf(buf, "%13s %c", arr[ndx].color, &c) == 2) {
            arr[ndx].value = c;
            ndx++;
        }
    }
    if (fp != stdin)
        fclose(fp);   

    for (size_t i = 0; i < ndx; i++)
        printf("arr[%2zu] : %s %d\n", i, arr[i].color, arr[i].value);

    //sorts the array
    qsort(arr, 26, sizeof(arr[26]), cmpfunc);
    for (n = 0 ; n < 26; n++) {   
        printf("%d ", arr[n].value);
    }

    //checks if arrays have the same element
    int j;
    for (j = 0; j < 26; j++) {
        if (arr[j].value != cmpvalues[j]) {
            printf("wrong");
            break;
        }
    }
    return 0;
}

input:

RED A
RED 2
RED 3
RED 4
RED 5
RED 6
RED 7
RED 8
RED 9
RED 10
RED J
RED Q
RED K
BLACK 10
BLACK J
BLACK Q
BLACK K
BLACK A
BLACK 2
BLACK 3
BLACK 4
BLACK 5
BLACK 6
BLACK 7
BLACK 8
BLACK 9

1 Ответ

0 голосов
/ 23 декабря 2018

Ваша функция сравнения неверна.

Функция qsort передает указатели на элементы в массиве, который вы сортируете, поэтому, если у вас есть массив colorval_t, тогда аргументыимеют тип colorval_t *.

Поскольку вы обрабатываете указатели int *, у вас есть несоответствие, и это приведет к неопределенному поведению .

Это означает, что ваша функция сравнения должна выглядеть примерно так:

int cmpfunc (const void * a, const void * b) {
    colorval_t *first = (colorval_t *) a;
    colorval_t *second = (colorval_t *) b;

    return first->value - second->value;
}
...