How do I sort this array of pointers without changing the sort of the original array?
I made this file to work out some confusion I had with pointers and arrays of pointers. I understand up until the commented out code, and am able to change the order of the values in p_to_pointers without changing p_to_nums. But I'm having trouble translating it to qsort.
Here is my output:
0 p_to_nums: 7 p_to_pointers: 7
1 p_to_nums: 4 p_to_pointers: 4
2 p_to_nums: 4 p_to_pointers: 4
3 p_to_nums: 2 p_to_pointers: 2
4 p_to_nums: 1 p_to_pointers: 1
This is the desired output:
0 p_to_nums: 4 p_to_pointers: 7
1 p_to_nums: 2 p_to_pointers: 4
2 p_to_nums: 7 p_to_pointers: 4
3 p_to_nums开发者_开发百科: 4 p_to_pointers: 2
4 p_to_nums: 1 p_to_pointers: 1
And my code:
int compare_values (const void *a, const void *b) {
    const int *int_a = (const int *) a;
    const int *int_b = (const int *) b;
    return (*int_b > *int_a) - (*int_b < *int_a);
}
main() {
    int i;
    int nums[5];
    int *p_to_nums;
    int *p_to_pointers[5];
    nums[0] = 4;
    nums[1] = 2;
    nums[2] = 7;
    nums[3] = 4;
    nums[4] = 1;
    p_to_nums = &nums[0];
  for (i=0; i< 5; i++) {
        p_to_pointers[i] = &p_to_nums[i];
  }
    //p_to_pointers[0] = &p_to_nums[2];
    //p_to_pointers[2] = &p_to_nums[0];
    qsort(*p_to_pointers, 5, sizeof(int), compare_values);
    for (i=0; i< 5; i++) {
        printf("%d p_to_nums: %d p_to_pointers: %u\n", i, (p_to_nums[i]), *p_to_pointers[i]);
  }
  return 0;
}
You are sorting *p_to_pointers with sizeof(int) whereas I believe you want to sort p_to_pointers sizeof(int *).
compare_values would need to be adjusted to dereference twice.
If…and this is a big if…I understand what you are trying to do.
Also, your comparison in compare() is needlessly complex. You can just do a simple subtraction instead of two comparisons and a subtraction.
int compare_values (const void *a, const void *b) {
  const int **int_a = (const int **) a;
  const int **int_b = (const int **) b;
  return (**int_b - **int_a);
}
main() {
  int i;
  int nums[5];
  int *p_to_nums;
  int *p_to_pointers[5];
  nums[0] = 4;
  nums[1] = 2;
  nums[2] = 7;
  nums[3] = 4;
  nums[4] = 1;
  p_to_nums = &nums[0];
  for (i=0; i< 5; i++) {
    p_to_pointers[i] = &p_to_nums[i];
    printf("%d p_to_nums: %d p_to_pointers: %u\n", i, (p_to_nums[i]), *p_to_pointers[i]);
  }
  qsort(p_to_pointers, 5, sizeof(int *), compare_values);
  for (i=0; i< 5; i++) {
    printf("%d p_to_nums: %d p_to_pointers: %u\n", i, (p_to_nums[i]), *p_to_pointers[i]);
  }
  return 0;
}
Output:
0 p_to_nums: 4 p_to_pointers: 4
1 p_to_nums: 2 p_to_pointers: 2
2 p_to_nums: 7 p_to_pointers: 7
3 p_to_nums: 4 p_to_pointers: 4
4 p_to_nums: 1 p_to_pointers: 1
0 p_to_nums: 4 p_to_pointers: 7
1 p_to_nums: 2 p_to_pointers: 4
2 p_to_nums: 7 p_to_pointers: 4
3 p_to_nums: 4 p_to_pointers: 2
4 p_to_nums: 1 p_to_pointers: 1
The first argument to qsort is *p_to_pointers.  That is the same as p_to_pointers[0] which you have set to &p_to_nums[0].  That, in turn is the same as p_to_nums.  So you call to qsort ends up being equivalent to
qsort(p_to_nums, 5, sizeof(int), compare_values);
Thus, you are sorting p_to_nums.
What you want is
qsort(p_to_pointers, 5, sizeof(int*), compare_values);
Then your compare_values has to convert the void* to int** rather than int*, and you need an extra level of indirection in your dereferences.  The usual way to accomplish the comparison would be something like this:
int compare_values (const void *a, const void *b) {
    const int **int_a = a;
    const int **int_b = b;
    return **int_b - **int_a;
}
Note that in C the casts from void* are not necessary (though in C++ they are).  Also note the more typical subtraction in the return statement, rather than your rather unusual construct (though yours works).
 
         加载中,请稍侯......
 加载中,请稍侯......
      
精彩评论