二、面向对象编程(OOP)

二、面向对象编程(OOP)(共18项)

1.C/C++中面向对象的相关知识
2.什么是纯虚函数抽象类
3.什么是多态?多态有什么作用?
4.重载和覆盖有什么区别?
5.C++中类默认有哪些成员函数?
6.C++中哪一种成员变量可以在一个类的实例之间共享?
7.继承层次中,为什么基类析构函数是虚函数?
8.面向对象技术的基本概念是什么,三个基本特性是什么?
9.为什么构造函数不能为虚函数?
10.虚函数是什么?为什么不能把所有函数设为虚函数?
11.什么是多态?多态有什么作用?
12.什么是公有继承、受保护继承、私有继承?
13.什么是虚指针?
14.C++如何阻止一个类被实例化?
15.类使用static成员的优点,如何访问?
16.一个父类写了一个virtual函数,如果子类覆盖它的函数不加virtual,也能实现多态?在子类的空间里,有没有父类的这个函数,或者父类的私有变量?
17.多态实现方式是什么?
18.C++对象模型、虚表、虚指针在插件化推理框架中有什么意义?

 

结论先行

这18个问题串起了 C++ 面向对象编程的“三板斧”:封装、继承、多态

  • 封装决定类/对象如何隐藏状态、暴露接口;
  • 继承实现代码复用与“是一个(is-a)”关系;
  • 多态让基类指针能调用子类实现,核心实现靠 虚函数 + 虚表 + 虚指针

在插件化推理框架中,这些机制正好用来定义稳定的抽象算子/后端接口(抽象类+虚函数),运行时通过虚表动态分派到不同插件实现,实现“接口不变、实现可插拔”。


逐条简明解释

1. C/C++ 中面向对象的相关知识

C 语言本身不是面向对象语言,但可以用结构体+函数指针模拟封装与多态。
C++ 原生支持:类、对象、封装、继承、多态、虚函数、抽象类、模板等。核心是把数据 + 操作数据的函数绑定在一起。

2. 纯虚函数与抽象类
virtual void foo() = 0;   // 纯虚函数

含有纯虚函数的类叫抽象类,不能直接实例化,只能被继承,强制子类实现接口。类似于 Java 的 interface 或 Python 的抽象基类。

3. 什么是多态?有什么作用?

多态就是“同一接口,不同表现”。

  • 编译时多态:函数重载、模板。
  • 运行时多态:虚函数 + 基类指针/引用。

作用:降低耦合、增强扩展性,写通用代码时不必关心具体子类类型。

4. 重载(Overload)与覆盖(Override)的区别
维度重载覆盖
发生范围同一作用域内基类与派生类之间
函数签名必须不同(参数列表不同)必须相同(除协变返回)
关键字不需要 virtual基类函数必须 virtual
绑定时机编译期运行期
5. C++ 类默认有哪些成员函数?

编译器会在需要时自动生成:

  1. 默认构造函数
  2. 拷贝构造函数
  3. 拷贝赋值运算符
  4. 移动构造函数(C++11)
  5. 移动赋值运算符(C++11)
  6. 析构函数

C++11 起,可用 = default 显式默认、= delete 显式删除。

6. 哪种成员变量可在类实例之间共享?

static 成员变量。
所有对象共用同一份存储,不属于某个对象,需在类外定义并初始化。

class A { static int count; };
int A::count = 0;   // 类外初始化
7. 为什么基类析构函数应为虚函数?

如果基类指针指向派生类对象,用 delete base_ptr 释放时:

  • 析构函数不是虚函数 → 只调用基类析构,派生类资源泄漏。
  • 析构函数是虚函数 → 通过虚表正确调用派生类析构,再调基类析构。

原则:有虚函数的类、或会被多态删除的基类,析构函数必须为 virtual

8. 面向对象的基本概念与三大特性
  • 基本概念:类、对象、封装、继承、多态、消息传递。
  • 三大特性封装、继承、多态
9. 为什么构造函数不能为虚函数?
  • 构造时对象类型还未完整,虚表尚未构建完成,无法动态分派。
  • 虚函数调用依赖虚指针,而虚指针正是在构造函数中初始化的。
  • 从语义上,派生类构造需要先构造基类部分,基类构造期间并不知道自己是派生类。
10. 虚函数是什么?为什么不能把所有函数设为虚函数?

虚函数是在基类声明为 virtual、允许派生类重写并通过基类指针动态调用的成员函数。

不能全部设为虚函数的原因:

  • 性能开销:每次调用需查虚表,有间接跳转和缓存未命中。
  • 对象体积:每个对象额外增加虚指针。
  • 设计语义:很多函数不需要多态,强制虚函数破坏内联和静态优化。
11. 同 3,略。

一句话:接口统一,实现可变,扩展方便

12. 公有、受保护、私有继承
继承方式基类 public 成员基类 protected 成员基类 private 成员语义
public 继承publicprotected不可见is-a 关系
protected 继承protectedprotected不可见实现细节复用
private 继承privateprivate不可见has-a / 实现继承

默认 class 私有继承,struct 公有继承。

13. 什么是虚指针?

每个含虚函数的类对象,编译器会隐式插入一个 虚指针(vptr),指向该类的 虚函数表(vtable)。通过它实现运行时多态。

14. C++ 如何阻止一个类被实例化?
  • 构造函数设为 private 或 protected(单例、工厂常用)。
  • 声明纯虚函数,使其成为抽象类。
  • C++11 起可用 = delete 删除构造函数。
class NonInstantiable {
public:
    NonInstantiable() = delete;
};
15. static 成员的优点与访问方式

优点:

  • 所有对象共享,节省内存。
  • 可作为全局状态/计数器,作用域限定在类内,避免命名污染。
  • 类级行为,不依赖对象实例。

访问:

ClassName::staticVar;       // 推荐
obj.staticVar;              // 也可通过对象访问,但语义上是类共享
16. 子类覆盖父类 virtual 函数时不加 virtual,能否多态?子类空间里有没有父类函数/私有变量?
  • 能实现多态。在 C++ 中,只要基类函数是 virtual,派生类中同名同签函数会自动成为虚函数(建议显式加 override)。
  • 子类对象空间里包含父类子对象:父类的非静态成员变量都会存在,包括私有变量,只是派生类无法直接访问。
  • 父类的虚函数在 vtable 中会被子类版本覆盖/替换,但父类自己的实现仍作为独立函数存在,可通过作用域调用:Base::foo()
17. 多态的实现方式
  1. 静态多态:函数重载、运算符重载、模板(编译期确定)。
  2. 动态多态:虚函数 + 虚表 + 虚指针(运行期确定)。
18. C++ 对象模型、虚表、虚指针在插件化推理框架中的意义

插件化推理框架常见设计:

  • 定义抽象基类 OpBackendInferenceEngine,包含纯虚接口。
  • 各后端/算子以动态库(.so/.dll)形式实现并继承这些基类。
  • 主程序通过 dlopen/dlsym 加载插件,返回基类指针/智能指针。
  • 虚表 + 虚指针保证运行期正确分派到插件具体实现,主程序无需重新编译即可接入新后端。

意义:

  • 解耦:核心框架与具体推理实现分离。
  • 可扩展:新增模型格式或硬件后端只需新增插件。
  • 统一接口:同一套推理 API 适配 CPU/GPU/NPU 等多种设备。

这些问题之间的联系

它们共同描绘了 C++ OOP 的完整图景:

类与对象
封装

继承

多态

虚函数

虚表 vtable

虚指针 vptr

抽象类/接口

插件化框架

  • 封装通过访问控制和构造函数管理对象状态。
  • 继承复用并扩展基类。
  • 多态让继承体系“活”起来,而多态依赖 vptr + vtable
  • 抽象类 + 虚析构为插件/框架提供安全、稳定的扩展边界。
  • static 成员则处理“类级别”的共享状态,与实例级状态互补。

掌握这些,你就能设计出像插件化推理框架这样“高内聚、低耦合、可扩展”的 C++ 系统。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值