【问题标题】:C- Sorting an array of pointers to integers that can be positive or negativeC-将指针数组排序为可以是正数或负数的整数
【发布时间】:2016-07-24 16:58:05
【问题描述】:

对于类,我需要在最小值和最大值之间生成一个包含 100 个整数的数组(现在可以正常工作),然后在一个单独的函数中,创建一个指针数组并按升序对其进行排序。

int *ptr是指向原始数组的指针,在头部定义SIZE为100

void sort(int *ptr){
    int *sortAr[SIZE] = { NULL };
    int i = 0, j, swap;
    for (i = 0; i < SIZE; i++)
        sortAr[i] = ptr[i];
    for (i = 0; i < (SIZE - 1); i++)
    {
        for (j = 0; j < SIZE - i - 1; j++)
        {
            if (sortAr[j] > sortAr[j + 1])
            {
                swap = sortAr[j];
                sortAr[j] = sortAr[j + 1];
                sortAr[j + 1] = swap;
            }
        }
    }
    int z = 0;
    for (z = 0; z < SIZE; z++)
        printf("%d\t", sortAr[z]);
}

当原始数组中的所有整数都是正数或负数时,我使用的代码可以正常工作,但是当存在混合时,它将对数组进行排序以包含按升序排列的正数,然后是所有负数升序。例如:

4       10      12      14      14      16      17      19      20      21
28      33      35      35      36      38      39      41      41      41
45      45      45      47      48      49      50      54      64      66
67      68      70      72      73      73      74      75      75      76
76      77      78      78      79      86      86      87      87      91
92      95      95      98      -100    -99     -92     -86     -86     -84
-82     -80     -78     -78     -76     -73     -73     -71     -70     -70
-69     -64     -63     -63     -58     -56     -53     -50     -49     -48
-44     -42     -36     -32     -30     -25     -24     -24     -21     -20
-20     -19     -17     -17     -10     -6      -5      -4      -3      -3

有什么想法吗?

【问题讨论】:

  • 你在做选择排序吗?你的嵌套for 循环不应该是这样的:for(i = 0; i &lt; (SIZE - 1); i++) for(j = (i + 1); j &lt; SIZE; j++) ...?看出区别了吗?
  • 使用指针数组对整数数组进行排序似乎有点奇怪。这个要求的目的是什么?
  • 你认为这段代码有什么作用? for (i = 0; i
  • 可能使原始数组未排序?
  • 我很确定这段代码并没有像你认为的那样做。 for (i = 0; i

标签: c arrays sorting pointers


【解决方案1】:

您已传入int 的原始数组,但您已将其复制到int* 的数组中。当您稍后比较这些时,您会有未定义的行为,因为您不允许比较指针,除非它们属于来自单个分配的同一内存块。

实际发生的是内部指针是unsigned,所以你的负值变成了很大的正值。幸运的是,该值被正确地转换回 int 以进行 printf 调用,因此更难看出您做错了什么(除非您阅读编译器的警告)。

改为这样声明你的数组:

int sortAr[SIZE];

【讨论】:

    【解决方案2】:

    将数组复制到指针数组中的方式是错误的。这是正确的方法:

    for (i = 0; i < SIZE; i++)
        sortAr[i] = &ptr[i];
    

    当你比较指针数组的内容时,你应该使用这种语法

    if (*sortAr[j] > *sortAr[j + 1]) { ... }
    

    打印内容时也是如此

    for (z = 0; z < SIZE; z++)
        printf("%d\t", *sortAr[z]);
    

    【讨论】:

      【解决方案3】:

      您根据存储在数组中的对数组进行排序。您当然可以使用指针数组reference 数组中的所有值,但要使用指针数组进行排序,您必须 dereference 指针,因此您实际上是根据值。

      例如,下面创建一个包含 -100 到 100 之间的 100 个值的随机数组,分配一个指针数组来引用这些值,然后使用指针数组对值进行排序:

      #include <stdio.h>
      #include <stdlib.h>
      #include <time.h>
      
      #define MAXI 100
      
      int main (void) {
      
          int arr[MAXI] = {0};
          int *arrp[MAXI] = {NULL};
          int i, j, swap;
      
          srand (time (NULL));
      
          for (i = 0; i < MAXI; i++) {            /* generate random values */
              arr[i] = rand() % (MAXI * 2 + 1) - MAXI; /* -100 < rand < 100 */
              arrp[i] = &arr[i];                  /* assign pointer value   */
          }
      
          printf ("\noriginal array - by pointers\n\n");
          for (i = 0; i < MAXI; i++) {
              if (i && !(i % 10)) putchar ('\n');
              printf (" %4d", *(arrp[i]));
          }
          putchar ('\n');
      
          for (i = 0; i < MAXI - 1; i++) {        /* sort pointer array */
              for (j = 0; j < MAXI - i - 1; j++) {
                  /* For decreasing order use < */
                  if (*(arrp[j]) > *(arrp[j + 1])) {
                      swap = *(arrp[j]);
                      *(arrp[j]) = *(arrp[j + 1]);
                      *(arrp[j + 1]) = swap;
                  }
              }
          }
      
          printf ("\nsorted array - by pointers\n\n");
          for (i = 0; i < MAXI; i++) {
              if (i && !(i % 10)) putchar ('\n');
              printf (" %4d", *(arrp[i]));
          }
          putchar ('\n');
      
          return 0;
      }
      

      使用/输出示例

      $ ./bin/bubblesort
      
      original array - by pointers
      
         55   88   94  -50   64  -64  -23   39   43  -67
        -75   44  -23   64   47  -18  -11  -50   76  -10
         32  -35  -53    9   95    8  -28   53  -39   32
        -88   67  -31  -94  -84  -68   93  -57   21   35
        -74   46  -22  -46    9   76   36   99  -75  -39
        -62    8   26  -65   67  -30   -6  -62  -77    5
         21   86  -29   90   92  -63   73   85  -19   -7
         19  -43  -61   48   11   48   23   97   -4   -2
        -43  -16  -95   33  -30   72  -97   64   61   77
        -32  -69   62  -10  -80    4   27   93  -12   58
      
      sorted array - by pointers
      
        -97  -95  -94  -88  -84  -80  -77  -75  -75  -74
        -69  -68  -67  -65  -64  -63  -62  -62  -61  -57
        -53  -50  -50  -46  -43  -43  -39  -39  -35  -32
        -31  -30  -30  -29  -28  -23  -23  -22  -19  -18
        -16  -12  -11  -10  -10   -7   -6   -4   -2    4
          5    8    8    9    9   11   19   21   21   23
         26   27   32   32   33   35   36   39   43   44
         46   47   48   48   53   55   58   61   62   64
         64   64   67   67   72   73   76   76   77   85
         86   88   90   92   93   93   94   95   97   99
      

      仅对指针排序

      如果您只想对指针数组进行排序而保持原始数组值不变,也可以通过比较 dereferenced 值来完成,但只交换指针:

      int i, j, *swap;
      ...
      for (i = 0; i < MAXI - 1; i++) {        /* sort pointer array */
          for (j = 0; j < MAXI - i - 1; j++) {
              /* For decreasing order use < */
              if (*(arrp[j]) > *(arrp[j + 1])) { /* compare values */
                  swap = arrp[j];                /* swap pointers  */
                  arrp[j] = arrp[j + 1];
                  arrp[j + 1] = swap;
              }
          }
      }
      
      printf ("\nsorted array - by pointers\n\n");
      for (i = 0; i < MAXI; i++) {
          if (i && !(i % 10)) putchar ('\n');
          printf (" %4d", *(arrp[i]));
      }
      putchar ('\n');
      
      printf ("\noriginal array\n\n");
      for (i = 0; i < MAXI; i++) {
          if (i && !(i % 10)) putchar ('\n');
          printf (" %4d", arr[i]);
      }
      putchar ('\n');
      

      使用指针打印将给出相同的排序顺序,但直接打印数组值将提供原始未排序的数组。例如:

      $ sorted array - by pointers
      
       -100  -99  -98  -98  -97  -95  -93  -93  -92  -86
        -86  -84  -81  -75  -73  -72  -67  -65  -64  -63
        -62  -59  -55  -53  -53  -52  -50  -48  -46  -42
        -40  -40  -37  -32  -31  -31  -28  -28  -27  -23
        -21  -20  -20  -17  -11   -9   -8   -6   -4   -4
         -1   -1    0    2    6   18   21   22   22   23
         24   26   26   28   29   33   34   34   34   36
         39   42   43   43   52   58   58   61   62   65
         67   70   70   73   79   80   80   80   80   81
         82   89   89   90   92   92   94   97   98  100
      
      original array
      
         80  -99   21  -98  -63  -52  -59  -73  -75    2
        -62  -53  -31   92  -31  -98  -32   36  -27  -28
        -21   22   -6  -53   92   29  100   97  -40  -86
        -64   90  -84   58   43  -97  -95   34   81   82
        -65  -81   79  -46   61   98  -93  -72  -17  -20
          0   62   52   94  -92   43   22   58  -11   33
         73   26  -28   89  -67  -86   42   89   -1   23
         70   34   -8   -1   39  -48   -4   -4  -20   80
         26   80   -9  -23   24  -50   70  -55  -93  -42
         28   80   34 -100   18   67   65  -40    6  -37
      

      你必须传递指针数组才能在函数中按指针排序

      您的函数的另一个问题是您正在传递一个指针(一个 int 数组),但是为了按指针数组排序,您必须将一个指针数组传递给排序函数(例如指针到指针-到整数)。要仅对函数中的指针数组进行排序,同时保持原始数组不变,可以使用以下命令:

      /* sort an array of 'n' pointers to int in 'a' */
      void psort (int **a, int n)
      {
          int i, j, *swap;
      
          for (i = 0; i < n - 1; i++) {        /* sort pointer array */
              for (j = 0; j < n - i - 1; j++) {
                  /* For decreasing order use < */
                  if (*(a[j]) > *(a[j + 1])) { /* compare values     */
                      swap = a[j];             /* swap only pointers */
                      a[j] = a[j + 1];
                      a[j + 1] = swap;
                  }
              }
          }
      }
      

      然后在上面的示例中,您可以将main() 中的排序替换为:

      psort (arrp, MAXI);
      

      对于仅排序指针的情况,这将导致上面发布的相同结果。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2015-06-11
        • 1970-01-01
        • 2017-02-12
        • 2017-07-16
        • 1970-01-01
        • 2011-03-19
        • 1970-01-01
        相关资源
        最近更新 更多