欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

Geekband C++面向对象高级程序设计-第四周作业

程序员文章站 2022-07-10 18:05:39
#题目说明: 分别给出下面的类型Fruit和Apple的类型大小(即对象size),并通过画出二者对象模型的方式来解释该size的构成原因。 #资料整理: Apple和Fruit对象内存分配: *注意点.编译器最终分配内存大小需要考虑"位对齐",规则如下: 1.首先按照声明次序依次保存类中数据对象。 ......

#题目说明:

   分别给出下面的类型Fruit和Apple的类型大小(即对象size),并通过画出二者对象模型的方式来解释该size的构成原因。

class Fruit {
    int no;
    double weight;
    char key;
public:
    void print() { }
    virtual void process() { }
};
  
class Apple: public Fruit {
    int size;
    char type;
public:
    void save() { }
    virtual void process() { }
};

#资料整理:  

Apple和Fruit对象内存分配:

*注意点.编译器最终分配内存大小需要考虑"位对齐",规则如下:

    1.首先按照声明次序依次保存类中数据对象。

  2.若类中存在虚函数在对象起始处会存在虚指针。

  3.变量的起始偏移位置设定为自身字节大小的整数倍,以便读取变量时使得cache速度更快。

  4.内存分配结束后,需要将当前内存空间补充为最大的基本类型变量的倍数。

*补充:在vs编译环境中,数据成员的起始地址必须为内部最大数据类型的整数倍。则存在虚指针时需要考虑补位对齐。

#作业发布:

  根据叶卡林娜的考虑方法,进行试验验证。

  思路整理:首先验证虚指针所存放在内存中的位置,及其占有内存单元。其次验证各个数据对象所在内存及其补位对齐方式。

需要注意,继承关系中虚指针是否单元新开辟的内存。

  测试代码如下:

#include <iostream>

using namespace std;

class Fruit {
public:
    int no;                                
    double weight;                           
    int key;                               
public:
    void print() { }
    virtual void process() {}
};

class Apple : public Fruit {
public:
    int size;                             
    int type;
public:
    void save() {   }
    virtual void process() {   }
};

int main() {
    cout << "sizeof(Fruit)   = " << sizeof(Fruit) << endl;
    cout << "sizeof(Apple)   = " << sizeof(Apple) << endl;
    Fruit fruit;
    Apple apple;
    cout << "Fruit           = " << &fruit << endl;
    cout << "Fruit.no        = " << &fruit.no << endl;
    cout << "Fruit.weight    = " << &fruit.weight << endl;
    cout << "Fruit.key       = " << &fruit.key << endl;
    cout << "Apple           = " << &apple << endl;
    cout << "Apple.no        = " << &apple.no << endl;
    cout << "Apple.weight    = " << &apple.weight << endl;
    cout << "Apple.key       = " << &apple.key << endl;
    cout << "Apple.size      = " << &apple.size << endl;
    cout << "Apple.type      = " << &apple.type << endl;
    system("pause");
    return 0;
}

 

win10 vs2017 运行结果如下:

sizeof(Fruit)   = 32
sizeof(Apple)   = 40
Fruit           = 003DF8D4
Fruit.no        = 003DF8DC
Fruit.weight    = 003DF8E4
Fruit.key       = 003DF8EC
Apple           = 003DF8A4
Apple.no        = 003DF8AC
Apple.weight    = 003DF8B4
Apple.key       = 003DF8BC
Apple.size      = 003DF8C4
Apple.type      = 003DF8C8

*补充:类中若存在虚函数(包括继承)则一定存在且仅存在一个虚函数指针指向虚表,虚表中存放虚函数地址。

#对象模型:

  根据上述摘要及测试代码整理,对象模型如下:

 

Geekband C++面向对象高级程序设计-第四周作业

#补充,无论堆中或者栈中构建的对象其内存大小均相同。