C中数组内部结构的动态内存分配

Dynamic Memory allocation of array inside structure in C

我正在用 C 语言做哲学家用餐问题以进行作业。我的代码一开始就卡住了。

我决定每个哲学家都是structure,forks是int数组。

但是我不能在这个赋值中使用全局变量。

所以,我必须在 philosopher 结构中包含共享变量,以便将它们传递给线程例程的参数。

这是我的问题 - 如果我在初始化时不知道它们的正确大小,如何在结构中包含 int 数组?

我的计划是在结构中包含指针变量,然后使用 & 分配数组地址。

但它不起作用:

#include <stdlib.h>

/* inside structure*/
typedef struct s_share {
    int **forks;
} t_share;

/* outside structure */
typedef struct s_philo {
    t_share *share;
} t_philo;


int main(void)
{
    t_philo *philo;
    int     *forks;
    int     i;

    i = 0;

    /* malloc structure arrary philo, size = 10 */
    philo = (t_philo *)malloc(sizeof(t_philo) * 10);

    /* malloc int arrary forks, size = 100 */
    forks = (int *)malloc(sizeof(int) * 100);
    while (i < 10)
    {
        philo[i].share->forks = &forks; //error
        i++;
    }

}

输出:分段错误

我像这样测试了 share->forks 大小:

printf("size of forks : %ld\n", sizeof(philo->share->forks));

输出为 8。 它的大小足以存储 int * 指针。 通过这个我知道不是内存分配的问题。

那问题是什么?有人可以帮我查一下吗?


编辑: 当我尝试直接 malloc philo->share->forks 时,我得到了同样的错误。

typedef struct s_share {
    int *forks;
} t_share;

typedef struct s_philo {
    t_share *share;
} t_philo;


int main(void)
{
    t_philo *philo;
    int     *forks;
    int     i;

    i = 0;
    philo = (t_philo *)malloc(sizeof(t_philo) * 10);
    while (i < 10)
    {
       philo[i].share->forks = (int *)malloc(sizeof(int) * 100); //error
        i++;
    }
}

我认为这是因为当 philo 初始化时,sizeof 运算符计算出 forks 的 memroy 为 8 - 这是指针所必需的。

有什么问题吗?


编辑 2: 为了解决我的问题,

这个问题很容易解决,如果我在结构定义中写上数组的大小。

typedef struct s_share {
    int forks[100];
} t_share;

typedef struct s_philo {
    t_share *share;
} t_philo;

但根据我的任务,我必须从 cmd 获取哲学家编号。所以我不能那样做。 以上是我的原始代码的简单版本


抱歉,编辑 2 有误:


typedef struct s_share {
    int forks[100];
} t_share;

typedef struct s_philo {
    t_share *share;
} t_philo;


int main(void)
{
    t_philo *philo;
    t_share *share;
    int     *forks;
    int     i;

    i = 0;
    philo = (t_philo *)malloc(sizeof(t_philo) * 10);
    while (i < 10)
    {
        philo[i].share->forks[i] = 1;
        i++;
    }
}

输出

zsh: segmentation fault  ./a.out

当我在结构定义中写入数组大小时,我仍然遇到段错误。

我使用 calloc 来初始化我的结构中的所有成员,但发生了同样的错误:

typedef struct s_share {
    int **forks;
} t_share;

typedef struct s_philo {
    t_share *share;
} t_philo;


int main(void)
{
    t_philo *philo;
    t_share *share;
    int     *forks;
    int     i;

    i = 0;
    philo = (t_philo *)calloc(10, sizeof(t_philo));
    forks = (int *)calloc(100, sizeof(int));
    while (i < 10)
    {
        philo[i].share->forks = &forks; //error
        i++;
    }
}

编辑 4: 我终于发现了错误。这是因为我没有在 philo struct

中 malloc 'share' struct
typedef struct s_share {
    int **forks;
} t_share;

typedef struct s_philo {
    t_share *share;
} t_philo;


int main(void)
{
    t_philo *philo;
    int     *forks;
    int     i;

    i = 0;
    philo = (t_philo *)malloc(sizeof(t_philo) * 10);
    forks = (int *)malloc(sizeof(int) * 100);
    while (i < 10)
    {
        philo[i].share = (t_share *)malloc(sizeof(t_share)); //here
        philo[i].share.forks = &forks;
        i++;
    }
}

这一行 -allocating struct share - 解决了问题。

或者,我可以像这样修改 philo 结构定义:

typedef struct s_philo {
    t_share share; //not pointer, just struct
} t_philo;

这样我就可以自动malloc struct share了

我在这一点上感到困惑。感谢您的帮助!

这一行

philo[i].share->forks

正在取消引用未设置的指针 'share'。你调用了 malloc 并且没有设置任何值,所以你分配的缓冲区中的数据是 'garbage' data.

// add begin
t_share* new_share = (t_share*)malloc(sizeof(t_share));
philo[i].share = new_share;
// add end

// don't use &forks
philo[i].share->forks = forks; //error
i++;
// need forks++
forks++;