C++的知识分享程序员C++

11. C++ 遮蔽、覆盖、重载

2019-04-05  本文已影响3人  飞扬code

11.1 重载

在同一个类中,或者在顶层函数(与main函数同层)中,如果函数名相同、参数不一致(类型、个数、顺序),则就是函数重载。
函数重载对函数返回值无要求,即返回值可以相同也可以不相同。
例如:

int function(int, char);
int function(char, int);
int function(int);
int function(char);

这四个函数相互之间构成了函数重载。
注意:函数重载返回值可以相同,也可以不相同!
例如:

int function(int, char);
char function(int);

构成函数重载

int function(int, char);
char(int, char);

这不算是函数重载,与返回值无关


11.2 覆盖(重写)

函数覆盖发生在继承层次之中。
覆盖需要满足的条件如下:
(1)发生覆盖的函数必须分别在父类和子类中
(2)子类函数与父类函数的函数相同,形参一致
(3)父类函数必须是虚函数覆盖对函数返回值同样没有要求,可以相同,也可以不同,但是很少有编译器支持这种特性

class A
{
  ……
  virtual int function(int, char)
{
  ……
}
  ……
};
class B::public A
{
  ……
  virtual int function(int, char)
{
  ……
}
  ……
};
int main(){
  A * one;
  B two;
  one = & two;
  one.function(int, char);
  return 0;
}

上面的例子就是一个覆盖,如果上面没有关键字virtual,那么调用的将会是class A 的函数函数覆盖说的就是多态。


11.3 遮蔽(隐藏)(重定义)

遮蔽是指子类中具有与父类同名的函数(不管参数列表是否相同),除去函数覆盖的情况。遮蔽的条件:
(1)子类的成员函数与父类的成员函数名必须相同
(2)子类的虚函数无法覆盖父类的虚函数遮蔽可以这么理解:

1)子类成员函数与父类成员函数具有相同的函数名
2)除去覆盖的情况遮蔽要求函数名一定相同,形参可以相同也可以不相同。
也就是说,继承层次中,父类与子类同名函数要么是覆盖,要么是遮蔽。

上例中如果没有virtual关键字,就属于遮蔽情况。或者上例中,子类function函数与父类函数形参不同,则也是遮蔽情况。

#include<iostream>
using namespace std;

//基类
Peopleclass People{
public:    
    void show();
protected:    
    char *name;    
    int age;
};
void People::show(){    
    cout<<"嗨,大家好,我叫"<<this->name<<",今年"<<this->age<<"岁"<<endl;
}

//派生类
Studentclass Student: public People{
public:    
    Student(char *name, int age, float score);
public:    
    void show(); //遮蔽基类的show()
private:    
    float score;
};
Student::Student(char *name, int age, float score){    
    this->name = name;   
    this->age = age;    
    this->score = score;
}
void Student::show(){    
      cout<<this->name<<"的年龄是"<<this->age<<",成绩是"<<this->score<<endl;
}
int main(){    
    Student stu("哈哈", 14, 95.0);    //使用的是派生类新增的成员函数,而不是从基类继承的    
    stu.show();    //使用的是从基类继承来的成员函数    
    stu.People::show();    
    return 0;
}

注意:基类成员和派生类成员的名字一样时会造成遮蔽,不管函数的参数如何。
换句话说,基类成员函数和派生类成员函数不会构成重载,如果派生类有同名函数,那么就会遮蔽基类中的所有同名函数,不管它们的参数是否一样。

总结:
(1)函数重载发生在同一个类或顶层函数中,同名的函数具有不同的参数列表
(2)函数覆盖发生在继承层次中,该函数在父类中必须是virtual,而子类的该函数必须与父类具有相同的参数列表
(3)函数遮蔽(隐藏)发生在继承层次中,父类和子类同名的函数中,不属于函数覆盖的都属于函数遮蔽

上一篇 下一篇

猜你喜欢

热点阅读