zoukankan      html  css  js  c++  java
  • 读书笔记深度探索C++对象模型Chapter5

    Chapter 5 构造析构拷贝语义学

    纯虚函数

    父类的纯虚函数仍然可以被定义并在子类中以静态方式调用。

    对于pure virtual destructor,类的设计者必须定义它,因为每个子类析构时会以静态方式调用其每一个virtual base class和上一层的base classdestructor(如果父类本身不为自己定义析构函数,链接时就找不到这个父类的析构实现,链接错误)。总之,不要把virtual destructor声明为pure

    继承体系下的对象构造

    T object;

    这样的代码在T的构造函数调用时,伴随着的动作有什么:

    1.  记录在member init list中的data member会被初始化。

    2.  如果有data member没有出现在member init list中,但是它有一个default ctor,则该default ctor会被调用。

    3.  在那之前,如果class objectvptr,则vptr需要被设定初值。

    4.  在那之前,所有上一层的base class ctor都被调用。

    5.  在那之前,所有virtual base class ctor必须被调用。

    如下继承结构下

    jc

     

    构造函数:

    PVertex::PVertex(float x, float y, float z) : _next(0), Vertex3d(x, y, z), Point(x, y) {

        if (spyOn)

           cerr << "within Point3d::Point3d()" << " size: " << size() << endl;

    }

    会被编译器扩展为:

    PVertex* PVertex::PVertex( Pvertex* this, bool __most_derived, float x, float y, float z )  {

        //有条件地调用virtual base classctor

        if ( __most_derived != false )

           this->Point::Point( x, y );

        //无条件地调用上一层的base classctor

        this->Vertex3d::Vertex3d( x, y, z );

        //初始化vptr

        this->__vptr__PVertex = __vtbl__PVertex;

        this->__vptr__Point__PVertex = __vtbl__Point__PVertex;

        //显式的用户代码

        if ( spyOn )

           cerr << "within Point3d::Point3d()"<< " size: "

                // 虚拟机制调用size()函数

                << (*this->__vptr__PVertex[ 3 ].faddr)(this)

                << endl;

        return *this;

    }

    对象复制语义学

    copy assignment operator

    如下的继承情况:

    classPoint3d : virtualpublicPoint {

    public:

       Point3d( float x = 0.0, y = 0.0, float z = 0.0 );

       ...

    protected:

       float _z;

    };

    编译器会为Point3d合成一个operator=(如果没有的话),合成的operator如下:

    inline Point3d& Point3d::operator=( Point3d *constthis, const Point3d &p ) {

       //调用base classoperator=

       this->Point::operator=( p );

       // memberwise copy the derived class members

       _z = p._z;

       return *this;

    }

    析构语义学 Semantics of Destructor

    如果class没有定义destructor,则只有class中的member object(或者classbase class)定义了dctor时,编译器才会为class合成一个dctor

    dctor的扩展:

    1.  dctor函数中的user code首先执行。

    2.  如果class中有member class object,而这个member class objectdctor,则这些member class objects会以声明顺序的逆序调用各自的dctor

    3.  如果object中有vptr,则需要被重新设定,指向适当的base classvtbl

    4.  上一层的nontrivial base classdctor会被调用。

    5.  如果有任何的virtual base classdctor,而该class是最尾端(most-derived)的class,那么它们会按照原来构造的逆序调用dctor

     

     

  • 相关阅读:
    VS2010中连接sdf数据库的字符串 Kevin
    找不到请求的 .Net Framework Data Provider。可能没有安装 Kevin
    MVC项目中找不到 DbContext 命名空间 Kevin
    Something About Assert()——C#中的断言 Kevin
    Html.Partial vs Html.RenderPartial & Html.Action vs Html.RenderAction Kevin
    .NET 中的双问号 Kevin
    苹果公司一道面试题 Kevin
    The diffrence between TempData and ViewBag and ViewData Kevin
    GRUB整体分析
    忠诚的成本看房产大鳄冯仑如何处理看待忠诚
  • 原文地址:https://www.cnblogs.com/apprentice89/p/2982942.html
Copyright © 2011-2022 走看看