【问题标题】:Notationally cleanest way of passing multidimensional array传递多维数组的符号上最干净的方法
【发布时间】:2014-12-11 17:01:50
【问题描述】:

我正在解决我在网上找到的这些问题,其中一个要求是就地旋转二维 NxN 数组。我的代码如下:

#include <stdio.h>

void rotate(int n, int *s)
{
   int nx, ny, tmp;
   int i, j;

   if(n < 1) return;

   /* Compute upper small square as basis for trajectories */
   if(n % 2 == 0) {
       nx = ny = n/2;
   }
   else {
       ny = (n-1)/2;
       nx = ny+1;
   }

   /* Move elements along their trajectories */
   for(i = 0; i < nx; i++) {
       for(j = 0; j < ny; j++) {
           tmp                      = *(s + n*j + n-1-i);
           *(s + n*j + n-1-i)       = *(s + n*(n-1-i) + n-1-j);
           *(s + n*(n-1-i) + n-1-j) = *(s + n*(n-1-j) + i);
           *(s + n*(n-1-j) + i)     = *(s + n*i + j);
           *(s + n*i + j)           = tmp;
       }
   }
}

int main(void)
{
    int test[4][4] = {
         { 1, 2, 3, 4 },
         { 5, 6, 7, 8 },
         { 9, 10, 11, 12},
         { 13, 14, 15, 16}};

    int n = 4;
    int i, j;

    for(i = 0; i < n; i++) {
        for(j = 0; j < n; j++) {
            printf("%d ", test[i][j]);
        }
        printf("\n");
    }

    printf("\nRotating matrix in place...\n\n");
    rotate(n, test);

    for(i = 0; i < n; i++) {
        for(j = 0; j < n; j++) {
            printf("%d ", test[i][j]);
        }
        printf("\n");
    }

    return 0;
}

我知道当我将二维数组传递给 main() 函数中的 rotate() 时,编译器会报错,因为从数组到指针的双指针转换。我的问题如下:

  1. 声明rotate()函数类型的正确方法是什么。

  2. 我怎样才能在函数 rotate() 中使用 s[i][j] 表示法而不必求助于指针算术?我意识到该类型必须能够以某种方式动态考虑n的值,所以有可能吗?

  3. 我知道我可以通过定义一对内联 getter 和 setter 函数来规避丑陋的表示法,但这需要输入太多。

【问题讨论】:

  • 我认为rotate(int n, int **s) 有效,它回答了 1/ 和 2/。
  • void rotate(int n, int *s[4]);
  • 但是,我倾向于避免不是数组数组而是呈现矩形矩阵的多维数组。将它们设为一维,并相应地调整您的代码;它让生活变得更轻松,尤其是当您开始为数组使用动态分配的内存时。
  • @Evert:我认为不会,因为编译器需要知道每行的长度来计算正确的索引。没有办法从 int **s 中推断出来。
  • 关于其他评论,是的,我通常也这样做。但是,我最近一直在用一种具有依赖类型的语言编写一些代码,这就是我开始使用这种方法的原因......我只是想知道它是否可以用 C 来完成(我认为 C89 不会不允许)

标签: c multidimensional-array


【解决方案1】:

将附加参数与指向数组的指针一起传递:

void Func( size_t y , size_t x , int(*a)[x] ) {...

这与

相同
void Func( size_t y , size_t x , int a[][x] ) {...

void Func( size_t y , size_t x , int a[y][x] ) {...

除了最外面的一个,必须为a 提供所有尺寸。在这种情况下,y 是可选的。但是你仍然需要它来确定函数中数组的外部大小。

符号与数组相同:

a[y-1][x-1] = 1234 ;

【讨论】:

    猜你喜欢
    • 2017-05-29
    • 1970-01-01
    • 2019-11-28
    • 1970-01-01
    • 1970-01-01
    • 2011-11-04
    • 2017-04-05
    • 2010-09-10
    • 1970-01-01
    相关资源
    最近更新 更多