C中定义不同的同名结构

Posted

技术标签:

【中文标题】C中定义不同的同名结构【英文标题】:Same name structure with different definition in C 【发布时间】:2016-01-27 10:06:35 【问题描述】:

是否允许在同一个项目的 2 个不同的 c 文件中使用具有不同定义的同名结构。例如。

文件1.c

typedef struct

    unsigned int unVar;             

 abc;

文件2.c

typedef struct

    int var;
 abc;

abc 用于两个文件。当我将这些文件编译为同一个项目的一部分时,没有错误,但我想了解这是否正确使用。

【问题讨论】:

不,没有重定义错误。 这里有一个类似的问题***.com/questions/3995940/…。 @anuj 如果它们在不同的编译单元中,并且如果您不在它们之间交换该数据(转换指针),那么它是安全的。如果这是一个好的做法......那是另一回事了。 【参考方案1】:

6.7.2.1 结构和联合说明符

    struct-or-union-specifier 中的 struct-declaration-list 声明了一个新类型, 在翻译单元内。

类型仅在翻译单元中定义,在本例中为 .c 文件。

在两个不同的翻译单元中定义两个同名的类型是没有问题的。

但是这两种类型是不兼容的,除非它们遵循 6.2.7., p1 中描述的规则。您定义的类型不兼容

【讨论】:

【参考方案2】:

这是类型定义。每个 .c 文件都是本地的,没有理由出错。必须在头文件中进行定义,这样就不会出现这样的问题。

【讨论】:

【参考方案3】:

符号的名称(变量、函数)在翻译单元中必须是唯一的。

翻译单元是CC++ 的基本编译单元。它由一个源文件以及所有包含的文件(直接或间接)组成。

在您的情况下,您有两个独立的源文件,每个文件都定义一个结构;但它们“看不到”对方,因为它们位于不同的翻译单元中。

但是,在链接过程中,如果目标链接对象之间存在多个同名符号(只要这些符号被导出,可以使用static 关键字修改),您可能会遇到麻烦。

【讨论】:

这适用于在全局范围内定义的符号,但可以在局部范围内重新定义符号:变量和结构标记或 typedef。【参考方案4】:

在两个不同的 *.c 文件中定义两个具有相同名称的结构是正确的用法,因为它们仅对定义它的 *.c 中的当前范围有效。

但我不建议这样做,以免您和任何其他必须使用两种同名类型并做其他事情的开发人员混淆。

【讨论】:

【参考方案5】:

每个定义对于它所在的文件都是本地的。由于您分别编译文件,编译器一次只能看到一个。将目标文件绑定在一起的链接器不验证类型一致性,它仅按名称解析符号。

如果要将st_localAscdData 或指向st_localAscdData 的指针传递给来自不同模块的函数,则必须确保不同模块中声明的类型之间的一致性。这就是头文件的目的。共享声明属于头文件,必须包含在共享给定类型或函数的所有模块中。

C 语言不强制执行全局类型一致性,C++ 在某种程度上也不强制,这是程序员的责任。编码规则是帮助程序员避免因这一缺点而陷入陷阱的指导方针。

【讨论】:

【参考方案6】:

您预计会出现重新定义的错误(在 cpp 编译器中会发生),但在 C 编译器中不会发生。 这个问题不仅发生在结构上,还发生在各种变量上。 我对此提出了一个问题,并有一些详细和高质量的答案。

Does C have One Definition Rule like C++?

【讨论】:

以上是关于C中定义不同的同名结构的主要内容,如果未能解决你的问题,请参考以下文章

编写同名方法

什么是方法重载?可以定义两个同名但参数类型不同的方法吗?

初学C++之虚函数及抽象类

C/C++语法知识点汇总

需要将多个(同名)域分类映射到不同的数据库模式

如何引用一个已经定义过的全局变量