3

我对动态内存分配和二维指针数组的删除感到非常困惑。

目标是拥有一个二维数组,其中每个单元格都有一个指向链表的指针。这就是我正在做的事情,我没有看到任何错误,但几乎没有警告。

警告:

1)

a value of type queue ** cannot be used to initialize an entity of type queue ***
queue* (**table) = (queue**)malloc(sizeof(queue*)*3);

2)

a value of type queue * cannot be assigned to an entity of type queue **
    table[indexI] = (queue*)malloc(sizeof(queue*)*3);

3)

a value of type queue ** cannot be assigned to an entity of type queue ***
  if( !(table = allocate()) ) {

这是代码:

queue **allocate() {

    queue* (**table) = (queue**)malloc(sizeof(queue*)*3);
    // Warning #1 at above line 
    for(.....) {

    table[index] = (queue*)malloc(sizeof(queue*)*3);
    // Warning #2 at above line. 
    }

    for(I index - 0 to 3) {
    for(J index - 0 to 3) {

    table[I][J] = NULL;

    }
    }
    return((queue**)table);
   }

    void deallocate(queue* **table) {


    // will handle list deletion
    // next deallocate table

    for(....) {
    free(table[index]);
    }
    free(table);

   }

void
add_list_to_queue(queue ***table) {

// here I create a list of queue type and assign it to
// those cells

}

modify_table() {

    queue* (**table) = NULL;

    table = allocate();
// Warning #3 at above line
.
.
.
    add_list_to_queue(table);

// do de allocation of table, list etc.,

    deallocate(table);

}

我在这些方面感到困惑

  1. 我不确定我对 2D 指针数组的声明是否正确
  2. 如何传递这个 2D 指针数组
4

2 回答 2

2

第一个警告是因为括号对表达式的 LHS 没有影响

queue* (**table) = (queue**)malloc(sizeof(queue*)*3);

table只是一个指向队列的三级指针。但是malloc返回一个指向内存块的指针,该内存块可以保存三个指向队列的指针,因此您正在为队列分配一个两级指针。

既然table是三级指针,table[indexI]就是二级指针。但是您对表达式的 RHS 不一致:

table[indexI] = (queue*)malloc(sizeof(queue*)*3);

malloc再次返回一个指向内存块的指针,该内存块可以保存三个指向队列的指针(即malloc返回一个两级指针),但您将其转换为一级指针,然后将其分配给两级指针.

至于第三个警告,您已定义allocate()为返回指向队列指针的指针,但您试图将其分配给table. 如上所述,table是一个三级指针,但allocate()只返回一个二级指针。

但实际上,这里不需要多级指针间接。把事情简单化。需要什么?指向行的指针,每行包含指向队列的指针。这就是 H2CO3 在他的评论中给你的建议:

queue *(*arr)[COLUMNS] = malloc(sizeof(*arr) * ROWS);

arr是一个指向 ROWS 数组的指针,每行包含指向 的 COLUMNS 指针queue

编辑:要将其传递给您在评论中询问的不同函数,首先声明并初始化指针:

queue* (*arr) [COLUMNS] = NULL;

然后要分配内存,请记住您需要更改指针指向的内容。因此,您必须将指针传递给指针。你的函数原型应该是:

void allocate (queue* (**arr) [COLUMNS]);  // Note the (**arr)

函数调用应该是:

allocate (&arr);

allocate()(为了使指针间接更容易,您可能希望使用我上面解释的 H2CO3 首次建议的格式声明和初始化一个不同的指向数组的指针,然后将该指针分配给*arr.)

请记住,您不仅必须为指向二维数组的指针分配内存,还必须为数组中的每个元素分配内存,因为该元素是未初始化的指针。您可以使用嵌套循环来执行此操作,allocate()或者,如果给定您的数据结构更合乎逻辑,则可以使用fill_table().

对于fill_table(),您可以简单地传递指向数组的指针本身。原型将是:

void fill_table (queue* (*arr) [COLUMNS]);

和电话:

fill_table (arr);

希望这可以帮助。做事最简单的方法可能是先在里面做所有事情process(),然后看看如何将分配和填充部分分离到它们自己的函数中。

于 2013-08-04T10:56:29.780 回答
0

1)您的第一个错误(queue* (**table))是您这里没有 2D 数组,而是 3D 数组,您的行可以这样写:queue ***table。因此,您只需要删除一个星号,然后您将声明一个 2D 数组指针。

2)第一反应,我想你不会再有这个警告了

3)这个错误和第一个一样,你只需要删除一颗星。

于 2013-08-04T10:57:34.843 回答