zoukankan      html  css  js  c++  java
  • 【C++】 overload、override、 overwirte

    一、 Overload(重载)


     在C++中,函数重载:函数名相同,但参数不同(包括类型、顺序不同),与函数返回值类型无关,例如Example中的f。满足条件:

    • 相同的范围(在同一个类中)
    • 函数名字相同
    • 参数不同

    二、Override(覆盖)

     在C++中,函数覆盖:对于基类中存在的一个virtual修饰的函数(例如Example中Base类存在g函数),用该基类的指针指向不同子类的类对象(Example的main函数中Base *pb指向Derived d),使用该函数会产生不同的响应结果(结果为子类中所要输出的结果),实际上这也是多态的一种体现,通常也叫做动态绑定。实现原理为:派生类函数覆盖基类函数,类中如果有带virtual关键字修饰的函数,则类中会有一张虚函数表vtable,当基类的virtual 修饰的函数在子类中重新实现后,会将vtable中原基类的函数用新函数来覆盖,若用基类指针指向子类对象时,会指向子类中基类所在的位置,此时基类中的virtual修饰的函数已经被子类实现的所覆盖,所以调用的结果是子类中函数,例如Example中的g。满足条件:

    • 不同的范围(分别位于派生类与基类)
    • 函数名字相同
    • 参数相同
    • 基类函数必须有virtual 关键字

    三、Overwrite(重写)

     重写是指派生类的函数隐藏了与其同名的基类函数。函数为no virtual,只要派生类中存在与基类同名的函数,则发生overwrite,如果有virtual 同名且同参,则发生Override,若同名不同参数发生overwrite。在Example const在派生类中的virtual函数中,同名的普通函数与const函数本质上是两个不同的函数,应该等价理解为这两个同名函数的参数是不同的。
      注意发生overwrite,函数行为依赖于指针/引用的类型而不是指向对象的类型。发生override则取决于指向的对象。

    四、多态

     C++ 多态意味着调用成员函数时,会根据调用函数的对象的类型来执行不同的函数。有了多态,您可以有多个不同的类,都带有同一个名称但具有不同实现的函数,函数的参数甚至可以是相同的。具体为可参考 override 。

    Example
    #include <iostream>
    using namespace std;
    
    class Base
    {
    public:
        void f(int x){ cout << "Base::f(int) " << x << endl; }
        void f(float x){ cout << "Base::f(float) " << x << endl; }
        virtual void g(void){ cout << "Base::g(void)" << endl;}
    };
    
    class Derived : public Base
    {
    public:
        virtual void g(void){ cout << "Derived::g(void)" << endl;}
    };
    
    int main()
    {
        Derived  d;
        Base *pb = &d;
        pb->f(42);        // Base::f(int) 42
        pb->f(3.14f);     // Base::f(float) 3.14
        pb->g();          // Derived::g(void)
    
        return 0;
    }
    
    Example const
    #include <iostream>
    using namespace std;
    
    class Base
    {
    public:
        virtual void f(float x){ cout << "Base::f(float) " << x << endl; }
    };
    
    class Derived : public Base
    {
    public:
        virtual void f(float x) const { cout << "Derived::f(float) " << x << endl; }//未发生override,而是Overwrite
    };
    
    int main()
    {
        Derived  d;
        Base *pb = &d;
        Derived *pd = &d;
    
        // Bad : behavior depends solely on type of the object
        pb->f(3.14f); // Base::f(float) 3.14
        pd->f(3.14f); // Derived::f(float) 3.14
    
        return 0;
    }
    
    Example 多态
    #include <iostream> 
    using namespace std;
     
    class Shape {
       protected:
          int width, height;
       public:
          Shape( int a=0, int b=0)
          {
             width = a;
             height = b;
          }
          virtual int area()
          {
             cout << "Parent class area :" <<endl;
             return 0;
          }
    };
    class Rectangle: public Shape{
       public:
          Rectangle( int a=0, int b=0):Shape(a, b) { }
          virtual  int area ()
          { 
             cout << "Rectangle class area :" <<endl;
             return (width * height); 
          }
    };
    class Triangle: public Shape{
       public:
          Triangle( int a=0, int b=0):Shape(a, b) { }
          virtual int area ()
          { 
             cout << "Triangle class area :" <<endl;
             return (width * height / 2); 
          }
    };
    // 程序的主函数
    int main( )
    {
       Shape *shape;
       Rectangle rec(10,7);
       Triangle  tri(10,5);
     
       // 存储矩形的地址
       shape = &rec;
       // 调用矩形的求面积函数 area
       shape->area();
     
       // 存储三角形的地址
       shape = &tri;
       // 调用三角形的求面积函数 area
       shape->area();
       
       return 0;
    }
    
  • 相关阅读:
    Eclipse代码快捷键
    QuickBI助你成为分析师——计算字段功能
    怎么从Linux服务器上下载超过4G的文件?
    centOS7下Spark安装配置
    s3c2440裸机-清bss原理及实现
    s3c2440裸机-代码重定位(2.编程实现代码重定位)
    Markdown语法教程
    s3c2440裸机-代码重定位(1.重定位的引入,为什么要代码重定位)
    s3c2440裸机-内存控制器(五、SDRAM编程实现)
    s3c2440裸机-内存控制器(四、SDRAM原理-cpu是如何访问sdram的)
  • 原文地址:https://www.cnblogs.com/Raowz/p/15744635.html
Copyright © 2011-2022 走看看