MST

星途 面试题库

面试题:C++非虚函数在继承体系中的使用特点

在C++的继承体系中,非虚函数有什么特点?请举例说明在哪些场景下适合使用非虚函数,以及使用非虚函数可能带来的潜在问题。
45.9万 热度难度
编程语言C++

知识考点

AI 面试

面试题答案

一键面试

非虚函数特点

  1. 静态绑定:在编译期确定调用哪个函数版本。即根据对象的静态类型(声明时的类型)来决定调用的函数,而非运行时对象的实际类型。
  2. 不可重写:派生类不能提供与基类非虚函数同名同参数列表的不同实现,否则会被视为隐藏基类函数(不是重写)。

适合场景

  1. 实现基本的、稳定的功能:例如,一个Date类用于处理日期相关操作,其getYear函数返回日期中的年份,这个功能通常是固定的,不会因派生类的不同而改变,适合定义为非虚函数。
class Date {
public:
    int getYear() {
        return year;
    }
private:
    int year;
};
  1. 强制派生类遵循特定行为:当希望所有派生类都以统一方式执行某个操作时,使用非虚函数。比如一个Shape类有一个drawOnConsole函数,用于在控制台简单绘制形状轮廓,所有派生的具体形状类(如CircleRectangle)都按此统一方式绘制,就可将drawOnConsole定义为非虚函数。
class Shape {
public:
    void drawOnConsole() {
        std::cout << "Drawing a shape outline on console" << std::endl;
    }
};

class Circle : public Shape {};

潜在问题

  1. 缺乏多态灵活性:如果需要根据对象实际类型执行不同行为,非虚函数无法满足。例如在图形绘制场景中,如果希望根据不同形状(CircleRectangle)执行不同绘制逻辑,使用非虚函数就无法实现运行时多态。
class Shape {
public:
    void draw() {
        std::cout << "Drawing a shape" << std::endl;
    }
};

class Circle : public Shape {
public:
    void draw() {
        std::cout << "Drawing a circle" << std::endl;
    }
};

Shape* shapePtr = new Circle();
shapePtr->draw(); // 输出 "Drawing a shape",而非 "Drawing a circle",没有体现多态
  1. 代码可维护性和扩展性受限:当派生类需要有不同行为但函数被定义为非虚时,修改代码可能比较麻烦,可能需要修改基类代码结构,违反开闭原则。