是“void * p =& p;”合法的C?

时间:2018-01-21 16:44:58

标签: c language-lawyer

我正在写一些列表库作为C中的练习。 我想知道C规范是否允许变量的声明和对它的引用,例如: -

typedef struct _List {
    int value;
    struct _List* next;
} List;

List* TERMINATOR = {0, &TERMINATOR};

简而言之,是否可以编写void* p = &p;

似乎gcc允许这样做,但我想知道规范是如何的。

提前谢谢。

2 个答案:

答案 0 :(得分:7)

void *p = &p;

有效。变量在它们自己的初始化范围内。

然而,

List* TERMINATOR = {0, &TERMINATOR};

无效,因为TERMINATOR是指针,而不是结构。

如果您删除*

List TERMINATOR = {0, &TERMINATOR};

有效。

参考:ISO 9899:1999, 6.2.1标识符范围

  
      
  1. 结构,联合和枚举标记的范围在外观之后开始   声明标记的类型说明符中的标记。每个枚举常量都具有该范围   在枚举器列表中出现其定义的枚举器之后开始。的不限   其他标识符的范围在其声明者完成之后开始。
  2.   

(强调我的)。

void *p = &p中,声明者为*p

答案 1 :(得分:5)

是的,这完全合法:

void* p = &p;

p标识符在其初始化块的范围内,因此获取其地址是完全合法的。

请注意,虽然这是允许的,但它非常不同寻常。到目前为止,终止列表的最常用方法是将next指针设置为NULL