0

我用c的可变长度数组实现一种算法:如何在堆上创建可变长度的数组?

int matrix[rows][cols]; 

我设法测试,这并失败的荒谬的尺寸。有没有办法在堆上分配这个矩阵而不是堆栈?否则,我将不得不重写这个到int** ...

有点像calloc(sizeof(int[rows][cols]), 1)?请注意,这个问题是关于变长数组的,特别是

+0

@ user3528438我问** **关于变长数组数据类型。另外,5D,认真吗? –

+4

适用于5D的东西可以简化为适用于2D。你有没有尝试'calloc(sizeof(int [rows] [cols]),1)'?你得到了多少尺寸?实际上,更重要的是打印'rows','cols'和'sizeof'表达式的值。它会给你你需要的东西吗?问题是“我将结果分配给什么”? –

+0

@TomášZato5D?是的,认真!为什么不? –

回答

2

看起来很简单。唯一远程棘手位是指针保持到动态分配的数组的类型:

#include <stdlib.h> 
#include <stdio.h> 

static void print_matrix(int r, int c, int matrix[r][c]) 
{ 
    for (int i = 0; i < r; i++) 
    { 
     for (int j = 0; j < c; j++) 
      printf(" %d", matrix[i][j]); 
     putchar('\n'); 
    } 
} 

static void set_matrix(int r, int c, int matrix[r][c]) 
{ 
    for (int i = 0; i < r; i++) 
    { 
     for (int j = 0; j < c; j++) 
      matrix[i][j] = (i+1) * 100 + j + 1; 
    } 
} 

int main(void) 
{ 
    size_t rows = 9; 
    size_t cols = 7; 
    size_t size = sizeof(int[rows][cols]); 
    printf("rows = %zu, cols = %zu, size = %zu\n", rows, cols, size); 
    int (*matrix)[cols] = calloc(sizeof(int[rows][cols]), 1); 
    if (matrix != 0) 
    { 
     set_matrix(rows, cols, matrix); 
     print_matrix(rows, cols, matrix); 
     free(matrix); 
    } 
    return 0; 
} 

此代码小心使用calloc()为零数组的所有元素,然后调用set_matrix()将它们设置为非零值。正如所写,malloc()会比calloc()更好,但使用的问题calloc()并且它也不难用于此代码(例如,set_matrix()中的条件赋值,如if (i && j && i != j))。

输出示例:

rows = 9, cols = 7, size = 252 
101 102 103 104 105 106 107 
201 202 203 204 205 206 207 
301 302 303 304 305 306 307 
401 402 403 404 405 406 407 
501 502 503 504 505 506 507 
601 602 603 604 605 606 607 
701 702 703 704 705 706 707 
801 802 803 804 805 806 807 
901 902 903 904 905 906 907 
1

您可以创建一个指向VLA:

size_t rows, cols; 
... // get values for rows and cols 
T (*arr)[cols] = malloc(sizeof (T [cols]) * rows); 
if (arr) 
{ 
    ... 
    arr[i][j] = some_value; 
    ... 
} 

有过是否

T (*arr)[cols] = malloc(sizeof *arr * rows); 

应该工作的一些争论。由于sizeof必须在运行时评估*arr(因为表达式*arr引用了VLA),因此在评估sizeof *arr时是无效指针,因此此表单的结果为未定义行为。

但是,它取决于“评估”在该特定上下文中的含义;没有理由要取消引用arr,以确定它指向数组的大小,任何超过你会为一个固定长度的数组:

T (*arr)[10] = malloc(sizeof *arr * rows); 

我和其他几个人是的认为该标准在这方面措辞不佳,并且sizeof *arr应该是有效的,无论arr指向固定的还是可变长度数组。这是我使用的成语,它并没有失败... 还有

但是,如果我没有指出这个问题,并且为您提供一些我知道将不会导致UB的情况,我将会失职。

相关问题