在另一个C文件中定义C结构体

3
我已经在我的头文件中声明了一个结构体,现在我想在另一个C文件中定义这个结构体的数组,以将其与我的主C文件分离。 按照我尝试的方式(见下面的代码),无法在第二个C文件中定义组件。如何在另一个C文件(或h文件)中定义结构体(但我认为h文件中不应该有定义)。

main.c

#include "struct.h"
int main(void)
{
    printf("%s",room[0].name);
    return 0;
}

struct.h

struct RoomStruct
{
    char name[20];
    int rRight, rLeft, rFront, rBack, rUp, rDown;
};
typedef struct RoomStruct Room;

extern Room rooms[20];

struct.c

#include <string.h>

#include "struct.h"

Room rooms[20];

strcpy(rooms[0].name,"firstRoom");
rooms[0].rLeft = 1;

2
如果你直接粘贴struct.c的代码... 你不能随意放置任何指令; 它们必须在函数内部。一个选项(也许不是理想的)是完全消除这些指令,而是使用完整的静态初始化来初始化rooms。但更好的方法是创建一个函数,要么是客户端代码必须调用以进行初始化,要么如果您的编译器支持非标准概念的通用构造函数,则利用它进行自动初始化。 - mah
1
“组件的定义不可能”是什么意思?你是否收到编译器错误?如果是,它是什么? - John Bollinger
顺便提一下,你声明了 rooms[20],但你尝试从 room 打印。这不是这段代码唯一的问题,但值得注意。 - embedded_guy
2个回答

1

正如 @mah 建议的那样,我建议您考虑调用函数来保持数据分离。这样做的附加价值是使“意大利面条式代码”远离您的代码库。例如,如果您有一个全局数组的 Room 结构体,它可以从任何地方调用。在文件中具有静态数组的 Room 结构体是更好的实践(依我之见)。以下是我制作的一个简单示例:

main.c

#include "struct.h"
#include <string.h>
#include <stdio.h>

int main (void)
{
    Room localRoom[20];

    strcpy(localRoom[0].name, "firstRoom");
    StructFunc_UpdateStruct(localRoom);
    strcpy(localRoom[0].name, "renamed");
    StructFunc_Print();
    printf("%s", localRoom[0].name);

    return 0;
}

struct.h

typedef struct
{
    char name[20];
    int rRight, rLeft, rFront, rBack, rUp, rDown;
} Room;

void StructFunc_UpdateStruct(Room * roomData);
void StructFunc_Print(void);

StructFunc.c

#include <string.h>
#include <stdio.h>
#include "struct.h"

static Room gRoom[20];

extern void StructFunc_UpdateStruct(Room * roomData)
{
    strcpy(gRoom[0].name, roomData[0].name);
}

extern void StructFunc_Print(void)
{
    printf("%s\r\n", gRoom[0].name);
}

I hope that helps! 编辑后的内容: 根据您的评论进行了编辑。 我猜测(基于您的评论)您想要能够根据不同的“.c”文件重新构建此程序,以便使用不同的“房间”。如果这是您想要实现的目标,那么这应该适合您:

main.c

#include "struct.h"
#include <stdio.h>

int main (void)
{
    printf("%s", rooms[0].name);
    return 0;
}

struct.h

#define NUM_OF_ROOMS    2
#define MAX_STRING_SIZE 20

typedef struct
{
    char name[MAX_STRING_SIZE];
    int rRight, rLeft, rFront, rBack, rUp, rDown;
} Room;

extern Room rooms[];

struct.c

#include "struct.h"

Room rooms[NUM_OF_ROOMS] =
{
    /* Room 0 */
    {
      /* Name       rRight  rLeft   rFront  rBack   rUp     rDown   */
        "Living",   1,      2,      3,      4,      5,      6
    },
    /* Room 1 */
    {
        "Dining",   2,      3,      4,      5,      6,      0
    }
};

更简单的构建格式

另一种选择是添加一个#define,这样你就不必改变正在构建的文件 - 只需更改#define的值,如下所示:

struct.h

#define MAP_NUMBER      0   //Change this value to use a different map.
#define NUM_OF_ROOMS    2
#define MAX_STRING_SIZE 20

typedef struct
{
    char name[MAX_STRING_SIZE];
    int rRight, rLeft, rFront, rBack, rUp, rDown;
} Room;

extern Room rooms[];

struct.c

#include "struct.h"

#if (MAP_NUMBER == 0)
Room rooms[NUM_OF_ROOMS] =
{
    /* Room 0 */
    {
      /* Name       rRight  rLeft   rFront  rBack   rUp     rDown   */
        "Living",   1,      2,      3,      4,      5,      6
    },
    /* Room 1 */
    {
        "Dining",   2,      3,      4,      5,      6,      0
    }
};
#elif (MAP_NUMBER == 1)
Room rooms[NUM_OF_ROOMS] =
{
    /* Room 0 */
    {
      /* Name       rRight  rLeft   rFront  rBack   rUp     rDown   */
        "Kitchen",   1,      2,      3,      4,      5,      6
    },
    /* Room 1 */
    {
        "Bathroom",   2,      3,      4,      5,      6,      0
    }
};
#else
Room rooms[NUM_OF_ROOMS] =
{
    /* Room 0 */
    {
      /* Name       rRight  rLeft   rFront  rBack   rUp     rDown   */
        "Bedroom",   1,      2,      3,      4,      5,      6
    },
    /* Room 1 */
    {
        "Dungeon",   2,      3,      4,      5,      6,      0
    }
};
#endif

嘿,谢谢回复。但我认为我没有正确指出实际问题..我的计划是有一个第二个c文件,可以轻松地被另一个文件替换,这样我就不必更改主文件来加载程序中数组“rooms”的另一个定义。 - winegum
@winegum,只是想澄清一下...您是否正在尝试拥有一个Room数组,该数组根据您使用的.c文件的不同版本进行初始化? - embedded_guy
谢谢!这正是我在寻找的,抱歉我的英语不好,让我难以澄清我的问题。我没有想到这种可能性。 - winegum
@winegum,没问题。我很高兴能帮到你! - embedded_guy

0
如mah所说,您不能仅将指令放置在任何函数范围之外的文件中。但是,您可以声明结构的实例。
至于如何引用在另一个文件中声明的变量,您可以使用extern关键字。

room.c

#include "room.h"
struct room my_room;

main.c

#include "room.h"
extern struct room my_room;

extern声明告诉编译器给定变量的内存是在其他待链接文件中定义的。虽然没有理由不在主函数中定义已经在另一个头文件中定义的结构体,但我不会像这样使用extern。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接