Warning while sorting a 2D array with qsort
Asked Answered
W

2

1

I'm trying to use qsort to sort a 2D array in C. The sort works, but I get the warning:

warning: initialization discards 'const' qualifier from pointer target type [enabled by default]

How can I modify my compare function to eliminate the warning (given that qsort requires the parameters const void *pa, const void *pb ?

int cmp (const void *pa, const void *pb ) {
  const int (*a)[2] = pa; // warning here
  const int (*b)[2] = pb; // warning here
  if ( (*a)[1] < (*b)[1] ) return 1;
  if ( (*a)[1] > (*b)[1] ) return -1;
  return 0;
}

I've read this post on Stack Overflow, but I'm still not sure how I should alter the compare function.

I have an array that looks like this:

int letterCount[26][2] = {{0, 0},{1, 0},{2, 0},{3, 0},{4, 0},{5, 0},{6, 0},{7, 0},{8, 0},{9, 0},{10, 0},{11, 0},{12, 0},{13, 0},{14, 0},{15, 0},{16, 0},{17, 0},{18, 0},{19, 0},{20, 0},{21, 0},{22, 0},{23, 0},{24, 0},{25, 0}};

Except in the second column, instead of zeroes, those are filled with other numbers. I'm trying to sort this 2d array by the second column, after 0s are filled in.

Whiteeye answered 22/9, 2013 at 18:39 Comment(0)
G
0

You could toy with the decls, but in the end I think this will suffice for the comparator you're using:

int cmp (const void *pa, const void *pb )
{
    const int *a = pa;
    const int *b = pb;
    if (a[1] < b[1]) 
        return -1;
    return (b[1] < a[1]);
}

Your data "items" are nothing more than int[] offsets in a 2D array. Were this a pointer array rather than a genuine 2D array, this would be considerably different. Grijesh was very close to this, only missing the [1] offsets (and the simple math), and if he undeletes his answers to fix it I'll just drop this.

Gefen answered 22/9, 2013 at 19:19 Comment(2)
Note that using subtraction like that runs the risk of overflow and consequent undefined behaviour if the values in the arrays are very large and of opposite signs. In practice, it isn't usually a problem, but be cautious. There's a trick for getting -1, 0 or +1 back using return (a[1] > b[1]) - (b[1] > a[1]); or thereabouts. Or you can do it the equivalent but clearer way: if (a[1] > b[1]) return +1; else if (a[1] < b[1]) return -1; else return 0; (which might even be more efficient since it only conditionally computes the second comparison).Ejaculation
Why the assignment const int (*a)[2] = pa; is giving warning ?Celindaceline
M
0

what is this supposed to do (*a)[2] ? it appears that you're dereferencing a pointer to an array in a declaration. here for a lack of better things to do I wrote my own version , I hope it'll help you :

#include <time.h>
#include <stdio.h>
    void Qsort(int matrix[][2] , int lenght)
    {
        if(!lenght)
                return;
        int temp = 0 , pivot , b = 0 , e = lenght - 1 , test = 0;
        const int MIN =0 , MAX = e;
        srand(time(NULL));
        test = (rand() % (MAX - MIN + 1)) + MIN;
        pivot = matrix[test][1];
        while(b < e)
        {
            while(matrix[b][1] < pivot)
                b++;
            while(matrix[e][1] > pivot)
                e--;
            temp = matrix[b][1];
            matrix[b][1] = matrix[e][1];
            matrix[e][1] = temp;
        }
        Qsort(matrix , b);
        Qsort(&(matrix)[b + 1] , lenght - 1 - b);

    }
Meatball answered 22/9, 2013 at 18:45 Comment(3)
The goal is to sort a 2D array by the second columnWhiteeye
what are you trying to do in those linesMeatball
creating an array of size two, (because I'm sorting a 2D array), then comparing the second element of eachWhiteeye
G
0

You could toy with the decls, but in the end I think this will suffice for the comparator you're using:

int cmp (const void *pa, const void *pb )
{
    const int *a = pa;
    const int *b = pb;
    if (a[1] < b[1]) 
        return -1;
    return (b[1] < a[1]);
}

Your data "items" are nothing more than int[] offsets in a 2D array. Were this a pointer array rather than a genuine 2D array, this would be considerably different. Grijesh was very close to this, only missing the [1] offsets (and the simple math), and if he undeletes his answers to fix it I'll just drop this.

Gefen answered 22/9, 2013 at 19:19 Comment(2)
Note that using subtraction like that runs the risk of overflow and consequent undefined behaviour if the values in the arrays are very large and of opposite signs. In practice, it isn't usually a problem, but be cautious. There's a trick for getting -1, 0 or +1 back using return (a[1] > b[1]) - (b[1] > a[1]); or thereabouts. Or you can do it the equivalent but clearer way: if (a[1] > b[1]) return +1; else if (a[1] < b[1]) return -1; else return 0; (which might even be more efficient since it only conditionally computes the second comparison).Ejaculation
Why the assignment const int (*a)[2] = pa; is giving warning ?Celindaceline

© 2022 - 2024 — McMap. All rights reserved.