【问题标题】:C pointer to 2d array指向二维数组的 C 指针
【发布时间】:2021-08-23 23:50:53
【问题描述】:

所以我正在创建一个循环,该循环可以通过将 [3][3] 数组的元素设置为枚举 EMPTY 来创建 3x3 板。在调试时,我可以看到程序在出现内存访问冲突错误之前正确设置了数组的前三个元素,所以我知道这是数组第二行的地址有问题(当 'i' 变量从 0 变为 1)。我该如何解决这个问题?指针对我来说仍然有点混乱。

int main(void)
{
    int board[3][3] = { 0, 0, 0, 0, 0, 0, 0, 0, 0 };
    int* p = &board;


    create_board(p);
    print_board(p);

    return 0;
}
void create_board(int *board)
{
    for (int i = 0; i < 3; ++i)
    {

        for (int k = 0; k < 3; ++k)
        {
            (&board)[i][k] = EMPTY;

        }
    }

    return;
}

【问题讨论】:

  • 你的编译器没有抱怨吗?发出任何警告?
  • 你认为这有什么作用? (&amp;board)[i][k] = EMPTY; 我特别想知道您对&amp; 的作用的理解。
  • 我知道 & 指的是地址,但我一直在玩 *board、(*board)、board 和 &board 实际编译,所以我只是坚持...:/
  • 没有必要从返回void的函数中return
  • &amp;board inside create_board 获取指针的地址,即局部变量board,从技术上讲,它位于堆栈的某个位置。该变量的地址与main 函数中的board 变量完全无关。如果您对该指针执行索引操作,您最终会到达您想要的任何其他位置。

标签: c pointers multidimensional-array implicit-conversion function-definition


【解决方案1】:

您的代码有很多问题。 C 中的数组不包含有关其大小的任何信息。

最简单的方法是使用指向数组的指针:

void create_board(size_t rows, size_t cols, int (*board)[rows])
{
    for (size_t i = 0; i < rows; ++i)
    {

        for (size_t k = 0; k < cols; ++k)
        {
            board[i][k] = EMPTY;
        }
    }
}

和主要的

int main(void)
{
    int board[3][3];
 
    create_board(3,3, board);
    print_board(3,3,board);
    return 0;
}

你可以用类似的方式编写print_board函数:

void print_board(size_t rows, size_t cols, int (*board)[rows])
{
    for (size_t i = 0; i < rows; ++i)
    {
        for (size_t k = 0; k < cols; ++k)
        {
            printf("[%zu][%zu] = %d\t", i, k, board[i][k]);
        }
        printf("\n");
    }
}

【讨论】:

  • 我个人更喜欢create_board(sizeof(board), sizeof(*board), board);,这样我们只有在创建数组时才有幻数。
【解决方案2】:

您的代码无效。编译器应该发出一条消息,指出此声明中使用了不兼容的指针类型

int* p = &board;

初始化表达式的类型为int ( * )[3][3],而初始化的对象的类型为int *

函数可以像这样声明

void create_board( int ( *board )[3], size_t n )
{
    for (size_t i = 0; i < n; ++i)
    {

        for (size_t k = 0; k < 3; ++k)
        {
            board[i][k] = EMPTY;

        }
    }
}

并像这样称呼

int ( *p )[3] = board;
create_board( p, 3 );

或者如果你的编译器支持可变长度数组,那么就像

void create_board( size_t m, size_t n, int ( *board )[n] )
{
    for (size_t i = 0; i < m; ++i)
    {

        for (size_t k = 0; k < n; ++k)
        {
            board[i][k] = EMPTY;

        }
    }
}

并像这样称呼

int ( *p )[3] = board;
create_board( 3, 3, p );

【讨论】:

  • @0___________ 我认为原因是对您问题的评论。
猜你喜欢
  • 2017-06-11
  • 1970-01-01
  • 1970-01-01
  • 2016-05-08
  • 1970-01-01
  • 2013-01-26
  • 1970-01-01
相关资源
最近更新 更多