什么决定对象大小?

lig*_*k76 4 c++ sizeof

我创建了包含整数和几个方法的简单对象,单独使用整数原始变量并比较它们的大小."sizeof()"表示返回值均为"4".为什么 - 不应该是复合类型的对象并包含有关方法的信息占用更多空间?

#include <iostream>

class Person{

    private:
        int a;

    public:

        void hello(){
            std::cout << "hello";
        }

        void DoSomething(){
            a++;
        }
};

int main(){

    int a;
    Person p;

    std::cout << sizeof(a) << std::endl;

    std::cout << sizeof(p) << std::endl;

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

vso*_*tco 10

这些方法(技术上是C++术语中的成员函数)不会影响对象的"大小".如果你考虑一下,这是有道理的.成员函数适用于从类或其后代实例化的任何对象,并且在某种意义上独立于实例.您可以将某个虚构类的成员函数Foo视为声明为的独立函数

return_type some_member_function(Foo* ptr, /* other params */){...}
Run Code Online (Sandbox Code Playgroud)

其中第一个参数是指向要应用函数的实例的指针.编译器实际上ptr在调用成员函数时隐式传递指针,所以

foo.some_member_function(/* other params */)
Run Code Online (Sandbox Code Playgroud)

正在被内部翻译为

some_member_function(&foo, /* other params */)
Run Code Online (Sandbox Code Playgroud)

您可以ptr通过关键字使用实际C++代码中指向的当前实例的地址this.从技术上讲,关键字this是一个prvalue表达式,其值是对象的地址,在该对象上调用成员函数.


PS:正如注释中提到的@greyfade一样,对象的大小可能仅通过virtual成员函数的声明来增加,因为在这种情况下,编译器必须在内部存储指向所谓的"虚拟表"的指针.无论虚拟功能是否被覆盖,都是这种情况.因此,如果您关心对象大小,请不要盲目地将析构函数设置为虚拟,除非您打算使用您的类作为层次结构中的基础.

  • `virtual`函数甚至不需要被覆盖才能产生效果.他们的存在只会产生一个vtable指针. (2认同)