虚空的大小是多少?

Lak*_*hmi 73 c c++ sizeof language-lawyer

这个陈述会产生什么?

void *p = malloc(sizeof(void));
Run Code Online (Sandbox Code Playgroud)

编辑:问题的扩展.

如果sizeof(void)在GCC编译器中产生1,那么分配1个字节的内存并且指针p指向该字节并且p ++将递增到0x2346?假设p是0x2345.我说的是p而不是*p.

rek*_*o_t 52

类型void没有大小; 这将是一个编译错误.出于同样的原因,你不能做类似的事情:

void n;
Run Code Online (Sandbox Code Playgroud)

编辑.令我惊讶的是,sizeof(void)实际上在GNU C 编译:

$ echo 'int main() { printf("%d", sizeof(void)); }' | gcc -xc -w - && ./a.out 
1
Run Code Online (Sandbox Code Playgroud)

但是,在C++中它没有:

$ echo 'int main() { printf("%d", sizeof(void)); }' | gcc -xc++ -w - && ./a.out 
<stdin>: In function 'int main()':
<stdin>:1: error: invalid application of 'sizeof' to a void type
<stdin>:1: error: 'printf' was not declared in this scope
Run Code Online (Sandbox Code Playgroud)

  • 但GCC可以选择对待'sizeof(void)== sizeof(char)'...参见-Wpointer-arith (27认同)
  • `sizeof(void)`是一个约束违规.符合标准的C编译器(默认情况下不是gcc)必须至少警告它,并且可能(和恕我直言)应该拒绝它.参考:[N1570](http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf)6.5.3.4p1(`void`是一个不完整的类型).自从1989年的标准引入了"void"以来就是这样. (5认同)
  • @Jon这是80年代初期刚刚开始学习如何编程的傻瓜.标准没有得到广泛的决定. (3认同)
  • @ unixman83:这没有意义.在1989年ANSI C标准引入之前,`void`不存在,这个标准使`sizeof(void)`违反了约束条件. (3认同)

hrn*_*rnt 39

如果您正在使用GCC而您没有使用删除编译器特定扩展的编译标志,sizeof(void)则为1. GCC具有非标准扩展,可以执行此操作.

通常,void是一个不完整的类型,并且您不能将sizeof用于不完整类型.

  • '-pedantic`隐含了选项`-Wpointer-arith`.我总是使用`-pedantic`.:) (2认同)

Kon*_*lph 15

虽然void可以为一种类型而设,但它实际上并不具有价值.因此,它在内存中没有大小.获取a的大小void未定义.

一个void 指针是一个简单的语言建构意义的指针,无类型的内存.


Kei*_*son 11

void没有大小.在C和C++中,表达式sizeof (void)无效.

在C中,引用N1570 6.5.3.4第1段:

sizeof不应将运算符应用于具有函数类型或不完整类型的表达式,此类型的带括号的名称,或应用于指定位字段成员的表达式.

(N1570是2011 ISO C标准的草案.)

void是一种不完整的类型.此段落是一个约束,这意味着任何符合要求的C编译器必须诊断任何违反它的行为.(诊断消息可能是非致命警告.)

C++ 11标准的措辞非常相似.这两个版本都是在提出这个问题后发布的,但规则可以追溯到1989年ANSI C标准和最早的C++标准.实际上,可能不适用void的不完整类型的规则sizeof可以追溯到引入void语言的程度.

gcc有一个扩展名,它被视为sizeof (void)1.默认情况下,gcc不是一个符合标准的C编译器,因此在默认模式下它不会发出警告sizeof (void).即使对于完全符合C编译器,也允许这样的扩展,但仍然需要诊断.

  • @GrzegorzSzpetkowski:(几年后回复。)是的,标准需要诊断,但默认情况下 gcc 不是符合标准的 C 编译器。从逻辑上讲,C 标准对不声称符合它的实现没有强加任何要求。gcc 可以(非常接近)符合正确的命令行选项,例如`-std=c11 -pedantic`。使用此类选项,它确实会发出所需的诊断信息。 (2认同)

pmg*_*pmg 10

采用void的大小是GCC扩展.


Ale*_*tov 5

sizeof()不能应用于不完整的类型.并且void是不完整的类型,无法完成.