为什么C++中空类的大小不为零?

shr*_*sva 74 c++ sizeof

可能重复:
C++:空类对象的大小是多少?

为什么以下输出1

#include <iostream>

class Test
{
};

int main()
{
    std::cout << sizeof(Test);
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

Pét*_*rök 115

该标准不允许大小为0的对象(及其类),因为这样可以使两个不同的对象具有相同的内存地址.这就是为什么即使是空类必须具有(至少)1的大小.

  • @Amigable,那么`测试[10];`有大小?并且`sizeof a/sizeof*a`将除以0.并且`for(Test*i = a; i!= a + 10; i ++)f(i);`也将无效.我相信它会导致很多问题,因为在编译器中需要很多特殊情况*和*在用户代码中. (13认同)
  • 嗯......但不管sizeof()返回什么,连接器都不应该能够处理它?这不是更像副作用吗?我明白你在说什么,但是对于sizeof(Test)来说,返回0并不是完全可行的.但如果标准这样说,那就是这么说的.实际上,对于曾经明确而不是故意模糊一个主题是一件好事. (2认同)
  • @ JohannesSchaub-litb:我不同意你的评论.sizeof a/sizeof*a将是0/0,这对于零大小类型将是一致的和"正确的"行为(这是因为无法区分Test a [10]和Test a [100],这是合乎逻辑的,因为它们是都退化}).for循环也不会失败.这是因为a + 10 = a.我没有看到任何与零大小类型的逻辑不一致,IMO不允许它们引入不一致.它的唯一优势可能只是要求所有对象都有不同的地址. (2认同)

Mau*_*ijk 35

确保两个不同对象的地址不同.出于同样的原因,"new"总是返回指向不同对象的指针.

请参阅Stroustrup以获得完整答案.


wil*_*ell 26

C++标准保证任何类的大小至少为1.C++标准规定没有对象与另一个对象具有相同的内存地址.这有几个很好的理由.

  1. 保证new始终返回指向不同内存地址的指针.

  2. 为了避免某些划分为零.例如,指针算术(其中许多由编译器自动完成)涉及除以sizeof(T).

但请注意,这并不意味着空基类会将派生类的大小加1:

struct Empty { };

struct Optimized : public Empty {
    char c;
};

// sizeof(Optimized) == 1 with g++ 4.0.1
Run Code Online (Sandbox Code Playgroud)

Bjarne Stroustrup也谈到了这一点.

  • @MSalters:迭代T类型的元素数组. (5认同)
  • 什么指针算术涉及`sizeof(T)`_dividing_?我想不出一个例子.Plase至少添加一个例子. (2认同)

小智 11

没有任何数据成员和成员函数的类这种类的类称为空类.空类对象的大小始终为1个字节.

当我们在那个时候创建​​任何类的对象时,对象总是得到3个特征,即

  1. 行为
  2. 身分

当我们在那个时候创建​​空类的对象时该对象的状态是什么.该对象的行为也没有,但编译器为该对象分配唯一的地址.计算机中的内存始终以字节的形式组织,对象地址位置可用的最小内存为1个字节.这就是为什么空类对象的大小是1个字节的原因.