繁体   English   中英

初始化并访问C中另一个结构内的嵌套结构char指针

[英]Initialize and access a nested struct char pointer within another struct in C

我的问题是在嵌套结构的初始化中,然后将其添加到该结构中。 我不知道如何正确访问该结构,甚至尝试对其进行初始化。 我可以使用malloc初始化第一个struct char指针,但是当我尝试以可以通过以下方式访问它的方式初始化嵌套struct时:

Rooms[i].Connected[i].conncet_room.

有一个细分,我通常的错误是:

下标值既不是数组也不是指针

这行代码是哪行:

Rooms[i].Connected[j].connect_room=(char*)malloc(sizeof(char*));

这是我正在使用的代码:

typedef struct Connections
{
    char* connect_room; 
} Connections;

typedef struct ROOM
{
   char*  name;
   char*  event;
   int connect_id;
   Connections Connected;
} ROOM;


main(){
    // creates memory space for 6 rooms.
    int sizeOf=6; 
    ROOM* Rooms = malloc(sizeOf*sizeof *Rooms);

    int i,j;
    for(i=0;i<sizeOf;i++)
    {
        Rooms[i].name=(char*)malloc(sizeof(char*));
        Rooms[i].event=(char*)malloc(sizeof(char*));
        for(j=0;j<sizeOf,j++)
            Rooms[i].Connected[j].connect_room=(char*)malloc(sizeof(char*));
    }
}

strcpy( Rooms[0].name, "kitchen"); // This works
strcpy( Rooms[0].Connected[0].connect_room, "hallway"); // This doesn't works
strcpy( Rooms[0].Connected[1].connect_room, "deck"); // This doesn't works

必不可少的我希望结构的结构如下:(以下内容仅是结构布局的示例,而非代码)

 Rooms[0]
     name --> "bed_room"
     event --> "sleep"
     Connected[0]
         connection_room --> "bath_room"
     ...
     Connected[5]
         connection_room --> "hall_way"

每个房间都有一个名称和一个事件,然后它将有1-6个connection_rooms。

最后,一旦嵌套结构成功初始化。 我该如何添加到.connect_room?

strcpy(Rooms[0].Connected[0].connect_room, "bath_room");

我正在用gcc编译

如果要每个房间有1-6个Connections项目,则需要更改ROOM声明。 您可以通过静态或动态分配来实现。

静态分配

typedef struct ROOM
{
    char* name;
    char* event;
    int connect_id;
    Connections Connected[6];
} ROOM;

// Don't need code to dynamically allocate Connected
for (j = 0; j < 6, j++) {
    // 256 is max size of connect_room string
    Rooms[i].Connected[j].connect_room = malloc(sizeof(char)*256);
}

如果您具有以下条件,则无需动态分配connect_room变量:

typedef struct Connections 
{
    char connect_room[256]; 
} Connections;

您也可以使用ROOMnameevent成员来执行此操作。

也许在更习惯于动态分配之前,您应该坚持使用静态分配。 您将需要释放所有动态分配的内存。

动态分配

typedef struct ROOM
{
    char* name;
    char* event;
    int connect_id;
    Connections* Connected;
} ROOM;

// To dynamically allocate Connected for each room:
Rooms[i].Connected = malloc(sizeof(Connections)*6);
for (j = 0; j < 6, j++) {
    // 256 is max size of connect_room string
    Rooms[i].Connected[j].connect_room = malloc(sizeof(char)*256);
}

它应该是

...
Connections * Connected;
...

看来您有固定数量的房间,您需要在运行时进行初始化。 每个房间的连接数似乎也最多。 在这种情况下,你不必malloc任何事情。 定义一个数组,并使连接成为指向该数组的指针。

C不擅长处理和查找字符串。 (好的,可以做的很好,但是字符串处理有点麻烦。)因此,我们不要将Room连接字符串做成字符串,而要指向其他房间的指针:

typedef struct Room Room;

#define MAX_CONN 6

struct Room {
   char *name;
   char *event;
   Room *conn[MAX_CONN];    // Connected rooms or NULL
};

连接最多MAX_CONN指向其他房间的MAX_CONN指针的数组。 未使用的插槽为NULL (您甚至可以定向连接,以便六个插槽分别指向北,东,南和西,楼上和楼下的出口。)

由于我建议不要使用字符串作为标识,因此我们将使用房间数组条目的序数。 裸数字有点不直观,因此让我们声明一个枚举值列表:

enum {
    Hallway,
    Bathroom,
    Bedroom,
    NRooms
};

NRooms房间名称声明为常数0、1和2,而NRooms是房间数3。

现在,房间数组声明:

int main()
{
    Room rooms[NRooms] = {
        [Hallway] = {
            .name = "Hallway", 
            .event = "loiter",
            .conn = {
                rooms + Bedroom,
                rooms + Bathroom
            }
        },
        [Bedroom] = {
            .name = "Bedroom", 
            .event = "sleep",
            .conn = {
                rooms + Hallway
            }

        },
        [Bathroom] = {
            .name = "Bathroom", 
            .event = "wash",
            .conn = {
                rooms + Hallway
            }

        }
    };

    room_print(&rooms[Hallway]);    // or: rooms + Hallway
    room_print(&rooms[Bedroom]);
    room_print(&rooms[Bathroom]);

    return 0;
}

初始化数组。 我在这里使用了指定的初始化程序 ,这是一种C99功能,可让您明确指定数组索引和结构成员名称。 这在这里有些夸张,但是如果您创建更多房间并向房间结构添加更多内容,这可能会很方便。 (在此示例中,所有内容均按顺序进行了初始化,因此您可以省略指定的初始化程序,而仅使用传统的位置初始化。)

rooms + x ”表示法使用指针算术来创建指向rooms数组中元素x的指针。 该表达式等效于&rooms[x]

未明确初始化的数组元素和结构元素被初始化为零或空值。 对于指针,则为NULL

最后, room_print例程将创建的数据结构付诸实践:

void room_print(const Room *room)
{
    int i;

    printf("This is the %s where you %s.\n",
        room->name, room->event);

    i = 0;
    while (i < MAX_CONN && room->conn[i]) {
        printf("A door leads to the %s.\n",
            room->conn[i]->name);
        i++;
    }

    printf("\n");
}

抱歉,由于您只询问了如何访问连接,所以有点冗长,但是我认为该示例说明了如何使用C初始化程序来实现类似该结构的示例布局。

当然,仍然可以在运行时更改数据。 没有什么可以阻止您说:

room[Bathroom].name = "Private bathroom";
room[Bathroom].conn[1] = Bedroom;
room[Bedroom].conn[1] = Bathroom;

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM