没有标签的结构的typedef每次使用时都会创建不同的类型,如果不是为什么?

时间:2016-01-27 19:21:31

标签: c struct language-lawyer typedef

我想知道你是否申报了这样的结构:

typedef struct 
{
    //...
} name;

那么,'name'类型的每个后续声明都会有不同的类型吗?

我想知道这是因为(来自标准)$ 6.7.2.3(p5):

  

结构,联合或枚举类型的两个声明   不同的范围或使用不同的标签声明不同的类型。的每个   声明结构,联合或枚举类型而不是   包含标签声明了一种不同的类型。

这是6.7.8美元(第3页):

  

在存储类说明符为typedef的声明中   声明器将标识符定义为表示的typedef名称   以6.7.6中描述的方式为标识符指定的类型。

所以这样的事情是非法的(尽管clang会接受它):

typedef struct{
    int a, b;
} s;

void func(s);

int main()
{
   s a = {2, 2};
   s b = a;
}

如果不是这样,请解释原因?

2 个答案:

答案 0 :(得分:4)

  

不包含标记的结构,联合或枚举类型的每个声明都声明了一个不同的类型。

这一行说的是每次声明这样的类型时,这都是一种新类型。并不是说每次声明这种类型的变量时,都会声明一个新类型。

您的代码只声明一次类型,因此它只创建一种类型。

答案 1 :(得分:4)

我认为你是误会

  

结构,联合或枚举类型的每个声明

这是结构类型的声明:

struct s1 {
    int a, b;
};

这是

typedef struct {
    int a, b;
} s2;

它也是typedef的声明。这是结构类型和对象的声明:

struct {
    int a, b;
} o1;

这不是结构类型的声明:

s2 o4, o5;

它是两个对象的声明,每个对象都有结构类型。但是这里没有声明结构类型。

标准特别说

  

struct-or-union-speci fi中的 struct-declaration-list 的存在在翻译单元中声明了一个新类型。

struct-declaration-list 是大括号内的所有内容。

所以这个也不是结构类型的声明:

struct s1 o2, o3;

同样,它声明了对象,并为它们提供了结构类型,但由于缺少 struct-declaration-list ,因此它不会声明类型。