zoukankan      html  css  js  c++  java
  • C++整理

    静态:

    (1)类静态数据成员在编译时创建并初始化,属于类,不属于某个对象,为所有对象所共享,包括该类派生类的对象,可以通过类名or对象访问。

    (2)static成员变量,可以实现同类对象间的信息共享。存储在数据段(data-rw){全局变量也是存储在data区},故而计算类大小时,不将其计算在内。

      (3) static成员可以产业能够为成员函数的可选参数{可选参数必须放在参数表的最右边},普通数据成员则不可以。

      

    1 void fun(int a,int b,int c=10);
    2     fun(1,2); //a=1,b=2,c=10
    3 
    4 void fun(int a,int b=10,int c);
    5     fun(1,2); //a=1,b=? c=?
    class base
    {
    public:
      static int static_var;
      int var;
      void foo1(int i=staitc_var);//正确
      void foo2(int i=var);//错误
    }

    (4)数据成员的类型和初始化方式:/cite https://www.nowcoder.com/questionTerminal/b73db04e98174120b50b5478839b3f8f?orderByHotValue=1&mutiTagIds=569&page=1&onlyReference=false

    static成员  初始化在类外,且不加static修饰
    const成员 只能在构造函数后的初始化列表中初始化
    const static成员 类只有唯一一份拷贝,且数值不能改变。因此,可以在类中声明处初始化,也可以像static在类外初始化

    (5)静态成员函数的意义,是在于管理静态数据成员,完成对静态数据成员的封装。因为非静态成员函数,在调用时this指针会被当做参数传入,静态函数成员属于类,不属于对象,无this指针,所以静态函数成员只能访问静态数据成员。

    (6)静态成员函数不可以同时声明为virtual,const,volatile函数。

      /cite http://www.jianshu.com/p/a3303c9ba748

           /cite http://www.cnblogs.com/Myhsg/archive/2009/07/31/1535650.html

    同步IO和异步IO:

    (1)同步IO,发出一个功能调用时,在没有得到结果之前,该调用就不返回。

    (2)异步IO,当一个异步调用发出后,通过状态、通知、回调函数来通知调用者。

    IOCP:

     (1)IOCP是一个异步I/O的API,可以高效地将I/O事件通知给应用程序。

    C/C++内存的申请释放:

    (1)malloc、free无法对非内部类型的对象自动执行构造函数、析构函数。

    (2)macllo、free是库函数,不是运算符,所以不在编译器控制权限之内。new、delete不是库函数,是运算符,所以拥有执行构造函数、析构函数的权限。

    (3)new出来的指针直接带类型信息,malloc返回的是void指针。

    指针和引用:

    (1)指针是一个变量,引用是一个别名。

    (2)引用必须在定义的时候初始化,之后不能改变。

    (3)引用不能为空,指针可以为空。

    (4)sizeof(指针)为指针本身的大小,sizeof(引用)所指向对象的大小。

    (5)不存在多级引用,引用不需要分配内存区域。

    多态:

    通过虚函数,在子类中通过重写的方式实现多态,实现根据对象的实际类型来调用相应的函数。

    (1)存在虚函数的类都有一个一维的虚函数表,类的对象有一个指向虚函数表的虚指针。

    (2)抽象类是至少包括至少一个纯虚函数的类。

    多态的实现原理:

    (1)早期绑定,静态绑定:编译器在编译的时候,需要确定每个对象调用(非虚函数)的地址。

    (2)假设存在父类P,父类对指针*pf。子类C,子类对象c。子类和父类具有同名函数say()。当指针pf指向对象c时,通过指针调用say(),会调用父类中的函数。

    class P
    {
    public:  
        void say()
        {
           std::cout<<"I'm father";
        }
    }
    class C:public P
    {
       void say()
       {
           std::cout<<"I'm children";
       }
    }
    void main()
    {
        C c;
        P *pf=&c;
        pf->say();
    }

    多态实现机制

    理解多态首先要理解类对象的内存模型。

    子类的对象内存模型是:父类的对象所占内存+子类的对象所占内存,所以当创建子类对象的时候,首先回去调用父类的构造函数,构造出父类的对象后,再调用子类的构造函数完成自身的构造。当将子类对象转换父类对象时,基于安全考虑,编译器会将该对象认为是子类对象模型的上半部分,也就是父类对象。所以使用类型转换后的对象指针调用函数的时候,会调用父类对象的函数。这些都是在编译期间决定的,为了达到对象和函数一一对应的目的,需要使用动态绑定,也就是使用多态。在基类中函数使用virtual关键字,此时子类会自动的在其同名函数上也加上,当然也可以手动添加virtual关键字。编译器会给有virtual关键字的类创建一个虚函数表(vtable){在构造函数中完成虚表的创建},里面以一维数组的形式记录了有virtual关键字的函数地址。为了定位vtable,编译器会给该类的每个对象提供了一个虚函数指针(vptr){在构造函数中完成虚指针的初始化},该指针指向了该对象所属类的vtable。

    在程序运行时,会根据对象的类型初始化虚指针{不使用多态特性时,会根据指针/引用类型来调用相关函数},使其指向正确的vtable。虚表可以继承,即使子类中没有重写虚函数,子类仍然具有该函数的地址,如果子类重写了该虚函数,那么新地址会覆盖继承下来的虚表中记录的虚函数原地址,如果子类新增了虚函数,对应的虚函数表中会增加对应项。回顾上文所述的对象内存模型,对象会首先执行父类的构造函数,完成父类对象的构造和父类的虚表和虚指针后,再进行自身的构造。

  • 相关阅读:
    大段程序注释C#、lisp
    AutoCAD VBA调用lisp
    团队作业(二):需求分析 Besti2019
    团队作业(三):确定分工 Besti2019
    [电子公文传输系统团队项目]团队作业(一) Besti2019
    2.4 OpenEuler中C语言中的函数调用测试
    团队作业(四):描述设计 Besti2019
    Web服务器1socket编程
    实验四 Web服务器2
    2017清华机试题——多项式求和(polynomial)
  • 原文地址:https://www.cnblogs.com/woaixuexiya/p/7769028.html
Copyright © 2011-2022 走看看