关于sizeof的一点理解

不小心看到网上很多关于sizeof的是表达式还是运算符之类的争论。

其实LZ也没法给出相应的结论。还是就说说它的特性跟用法吧!

https://msdn.microsoft.com/en-us/library/4s7x1k91.aspx

一、sizeof是在编译的时候就计算所占的空间大小,也就是说在给定的表达式必须在编译的时候就知道其大小(类型名则在编译的时候知道其大小)。既然是在编译的时候就知道其大小,那么sizeof里面的表达式或者通过某种方式获取到对应的类型名的过程,在运行过程中就不再进行运算。

比如:int a = 10; sizeof(++a); 在程序跑过sizeof(++a)的时候其实a还是等于10

二、关于计算的大小这个得看你的表达式或者类型名所占的空间大小。

比如:

int* p = new int[100]; sizeof(p) == 4;  因为p的类型是int* 占4个字节。而不是new出来的100*sizeof(int)

int* p[100]; sizeof(p) == 100*sizeof(int*)  这里其实可以看出p的类型是 int*(&)[100] 所以很简单的就可以知道所占据的空间大小了。

关于计算结构体的大小涉及的方面就比较多了(对齐等)这里就不多介绍了。

三、关于msdn给出的https://msdn.microsoft.com/en-us/library/4s7x1k91.aspx   

sizeof unary-expression
sizeof  ( type-name )
说明如果是一元表达式则不能加括号。如果是类型名则加括号。

1、关于最简单的 int a; 为什么sizeof(a)也合法 sizeof a 也合法呢?这里咱们可以发现编译器可以自然地识别出a是int类型所以说它是类型名,但是从另一个角度分析也可以说它是表达式:很通俗的一个说法就是你在程序的随便一行可以这么写:a;虽然a不做任何处理但是编译器却把它看成是一行语句。所以在这里使用sizeof(a) 跟 sizeof a都是没有问题。
2、网上经常给出的sizeof(int) 这个要加括号但是总是没给出原因。其实这里的Int它是类型名,却无法把它当做一个表达式,所以它就必须加括号。如果咱们这样子写 sizeof(int()) 那么就会编译出错。因为int()现在被当成了表达式,但不是类型名。因为int() 表达式的结果程序无法正常推出来是什么类型,如果说可以正常推出来那么char()它也应该要推出来是char类型,更一般的情况假设有一个结构体struct Node{};那么它应该也要推出来Node()是Node类型。但是编译器对于表达式推断结构体类型目前是无法做到的。所以编译器也不会对特化的表达式(char()、int()等等)进行相应的推断它的类型名。虽然sizeof(Node)和sizeof Node() 返回的结果是一样大的。
3、LZ在测试的过程中发现struct Node {Node(int){}}; 这样在执行 sizeof Node;按照正常的推理,把Node当成一个表达式。既然是表达式的话它需要一个参数,但是结构体却没有提供,理论上应该编译不通过的。但是真正编译的时候却没有报错。我们知道如果给定了构造函数,编译器就不会再自动生成对应默认构造函数。那么编译器是如何确定它是一个表达式的呢?LZ这里也不清楚。有一个牵强的解释是:编译器底层已经默认声明了无参的构造函数。当然这个只是猜测,路过的希望能提点一下。
原文地址:https://www.cnblogs.com/cxiaoln/p/4986118.html