结构和指向指针元素的指针

时间:2019-12-09 11:43:24

标签: c pointers structure

我正在为一个学校项目工作:

我必须使用此原型创建一个函数:

int ddg_add_player(ddg_t *ddg, player_t *player); 

这是ddg_t结构:

typedef struct
{
        int day; /**< The DDG date (day). */
        char *dmname; /**< The dungeon master name. */
        int month; /**< The DDG date (month). */
        char *name; /**< The DDG name. */
        int nplayers; /**< The DDG number of players. */
        player_t **players; /**< The DDG players. */
        int year; /**< The DDG date (year). */
} ddg_t;

因此,我必须将填充的player_t结构添加到ddg_t结构中。而且我不知道该如何处理,

我尝试过

ddg->players->ac = player->ac;

但这显然不起作用。

就本例而言,假设player_t如下:

typedef struct
{
        int ac; /**< The player armor class. */
} player_t;

我不知道为什么我必须使用这个player_t **players,并且我不能问我的老师,因为我会在这个项目上得到评估。

另一方面,由于我有多个玩家,所以我确实具有结构player_t的数组。

起初我以为我必须通过一种结构,而我的电话看起来像这样:

for(i = 0; i < nPlayers; i++) {
        ddg_add_player(&ddg, &players[i]);
    }

我的呼叫现在看起来像这样:

ddg_add_player(&ddg, players); /* players is my array of struct */

以及类似的功能:

int ddg_add_player(ddg_t *ddg, player_t *player){
    ddg->players = malloc(sizeof(player_t) * 3); /* i have 3 players */
    ddg->players[0]->ac = player[0].ac;
    printf("%d\n", ddg->players[0]->ac); /* just to check */

    return 0;
}

因此,该代码有效,但是在老师给的标头中说我必须同时添加一个播放器。

有办法吗?

我尝试了您的解决方案@chmike,但它给了我这个错误:

error: expected expression before ‘player_t’
 oc(ddg->players, (ddg->nplayers+1)*sizeof(*player_t));
                                            ^~~~~~~~

我尝试删除*,但是这给我带来了分段错误。

2 个答案:

答案 0 :(得分:2)

我假设您正在使用“指向指针元素的指针” player_t **players在此处存储指向多个玩家的指针数组?

在这种情况下,实际上是ddg->players->ac出现了问题,它不知道您要哪个播放器,那里还有一个间接级别。例如第一个玩家为ddg->players[0]->ac,第二个玩家为ddg->players[1]->ac

当然,您还需要在此处分别分配和释放ddg->players本身,例如ddg->players = malloc(sizeof(player_t*) * 5)代表5位玩家。然后您需要分别分配每个玩家指针,例如ddg->players[0] = first_player在其他位置创建播放器的位置。

ddg->players = malloc(sizeof(player_t*) * 2)
ddg->players[0] = amy;
ddg->players[1] = bill;
printf("%d %d", ddg->players[0]->ac, ddg->players[1]->ac);

现在,如果ddg_t应该“拥有” player_t,而每个player_t *players只能使用一次,则可以使用ddg->players = malloc(sizeof(player_t) * 3); ddg->players[0].ac = 14; ddg->players[1].ac = 18; ddg->players[2].ac = 20; 数组,从而摆脱了额外的间接和分配,但是您通常应该始终为索引指定索引,即使是第一项也是如此。

{{1}}

答案 1 :(得分:1)

ddg_t结构中,我们看到了字段

int nplayers; /**< The DDG number of players. */
player_t **players; /**< The DDG players. */

我们可以从中得出players是指向player_t的指针的指针。因此,players是指向玩家的指针数组,而nplayers是指向数组的元素数(指向player_t的指针)。

要添加新玩家,您需要将其追加到玩家数组中。这意味着阵列需要增长。这是通过使用realloc函数并将数组的新字节大小作为参数来完成的。

以下是该函数的代码:

int ddg_add_player(ddg_t *ddg, player_t *player){
    ddg->players = realloc(ddg->players, (ddg->nplayers+1)*sizeof(*player_t));
    ddg->players[ddg->nplayers++] = player;
}

第一条指令将players数组最后增加一个元素。

第二条指令将player递增之后,将nplayers分配给数组的最后一个元素。

函数终止时,players是附加了player的输入数组,并且nplayers已递增,因为它又包含一个播放器。