【问题标题】:Allocating a dynamic array inside a struct在结构内分配动态数组
【发布时间】:2019-04-02 21:26:26
【问题描述】:

我正在设置一个定义多项式的结构,即它包含两个变量:
-int degree 包含多项式的度数
-int * coeff = (int*) malloc (degree * sizeof(int)) 保存所有系数

我还定义了一个函数new_polynome(),它接受一个度数并返回一个指向一个结构的指针,该结构体保存该度数的多项式,其所有系数都设置为1;

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

// 1

typedef struct 
{
    int degree;
    int * coeff = (int *) malloc (degree * sizeof(int));
} polynome;


// 2

polynome * new_polynome(int n)
{
    polynome * newest_polynome = (polynome *) malloc (sizeof(polynome));
    for(int i = 0; i < n; i++)
        newest_polynome->coeff[i] = 1;

    return newest_polynome;
}

int main(void)
{
    polynome * new_polynome = (polynome *) malloc (sizeof(polynome));
    new_polynome = new_polynome(5);

    for(int i = 0; i < 5; i++)
        printf("%d", new_polynome->coeff[i]);

    free(new_polynome->coeff);
    return 0;
}


但是,当我尝试打印其系数时,出现以下错误。有没有正确的方法来做到这一点?我不明白错误信息。 如何打印它的系数? 我的错误如下:
TD_polynomes.c:9:17: error: expected ‘:’, ‘,’, ‘;’, ‘}’ or ‘__attribute__’ before ‘=’ token int * coeff = (int *) malloc (degree * sizeof(int)); ^ TD_polynomes.c: In function ‘new_polynome’: TD_polynomes.c:19:24: error: ‘polynome {aka struct <anonymous>}’ has no member named ‘coeff’ newest_polynome->coeff[i] = 1; ^~ TD_polynomes.c: In function ‘main’: TD_polynomes.c:27:20: error: called object ‘new_polynome’ is not a function or function pointer new_polynome = new_polynome(5); ^~~~~~~~~~~~ TD_polynomes.c:26:16: note: declared here polynome * new_polynome = (polynome *) malloc (sizeof(polynome)); ^~~~~~~~~~~~ TD_polynomes.c:30:34: error: ‘polynome {aka struct <anonymous>}’ has no member named ‘coeff’ printf("%d", new_polynome->coeff[i]); ^~ TD_polynomes.c:32:22: error: ‘polynome {aka struct <anonymous>}’ has no member named ‘coeff’ free(new_polynome->coeff); ^~

【问题讨论】:

  • 不能在结构的定义中初始化成员。 coeff 应该在 new_polynome 中初始化。此代码为两个polynome 分配内存并丢弃第一个。 new_polynome 变量屏蔽了同名函数。

标签: c struct malloc


【解决方案1】:

后面的错误只是前面的结果是很常见的,这里就是这种情况。您对多项式的定义有误。这导致它没有一个名为 coeff 的成员。

你不能以你的方式初始化一个结构。去掉结构体中的 malloc 调用,你会发现其他一些错误会神奇地消失。

这行:new_polynome = new_polynome(5); 没有意义。似乎您正在尝试为 5 个系数分配空间,但是您完全错了。你应该这样做`new_polynome->coeff = malloc(5*sizeof(*(new_polynome->coeff))

另外,don't cast malloc

您应该移动一些代码,例如分配系数。这应该进入 new_polynome 函数,我将其重命名为 create_polynome。

工作(和固定)代码:

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

typedef struct
{
    int degree;
    int *coeff; // No init here. You're just defining a type here.
} polynome;


polynome *create_polynome(int n)
{
    // A polynomial of degree 0 is a constant
    const int N = n+1;

   // You need to set the degree
    new_polynome->degree = n;

    polynome *new_polynome = malloc(sizeof(*new_polynome));
    new_polynome->coeff = malloc(N * sizeof(*(new_polynome->coeff)));
    for(int i = 0; i < N; i++)
        new_polynome->coeff[i] = 1;

    return new_polynome;
}

int main(void)
{
    polynome *new_polynome = create_polynome(5);
    // Looping to degree makes much more sense
    for(int i = 0; i < new_polynome->degree+1; i++)
        printf("%d", new_polynome->coeff[i]);

    free(new_polynome->coeff);
    // Not necessary to free in the end, but if you want to do it,
    // do it properly and free everything. One malloc for each free and
    // vice versa
    free(new_polynome);
    // No need  to return 0 since that's the default in main
}

我还做了一些很好的(主观而言)修改,比如在取消引用 * 和标识符之间没有空格。还删除了函数和括号之间的空间。另外,我使用了对象的大小而不是类型。

作为额外的奖励,一个衍生函数:

polynome *derivate_polynom(polynome *pol)
{
    polynome * derivate = create_polynome(pol->degree - 1);
    for(int i = 0; i < derivate->degree + 1; i++)
        derivate->coeff[i] = (i+1) * pol->coeff[i+1];
    return derivate;
}

【讨论】:

    【解决方案2】:

    1) int * coeff = (int *) malloc (degree * sizeof(int)); 在你的结构定义中是无效的语法:

    typedef struct 
    {
        int degree;
        int * coeff = (int *) malloc (degree * sizeof(int));
    } polynome;
    

    应该是:

    typedef struct 
    {
        int degree;
        int * coeff;
    } polynome;
    

    2) 这是错误的:

    polynome * new_polynome = (polynome *) malloc (sizeof(polynome));
    new_polynome = new_polynome(5);
    

    您将malloc 的结果分配给new_polynome,然后立即用new_polynome(5). 的返回值覆盖它,这是内存泄漏。

    3) 我认为您可能希望为 N+1 整数而不是 N 分配空间。零次多项式是一个常数。

    【讨论】:

      【解决方案3】:

      语法无效;你可以写

      typedef struct 
      {
          int degree;
          int coeff[];
      } polynome;
      
      polynome *new_polynome(int n)
      {
          polynome *p;
      
          p = malloc(sizeof *p + n * sizeof p->coeff[0]);
          for(int i = 0; i < n; i++)
              p->coeff[i] = 1;
      
          return p;
      }
      

      而不是。也许,当n 是不受信任的用户输入时检查溢出。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-04-18
        • 1970-01-01
        • 2021-10-30
        • 2017-03-30
        相关资源
        最近更新 更多