首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> C++ >> 關於C++

C++ 面試核心知識體系:基礎、面向對象、繼承、多態、虛表機制全景圖

     編輯:關於C++

一、基礎語法與內存模型

  • using namespace std:引入標準庫命名空間
  • 內部鏈接:static 函數/變量;外部鏈接:extern
  • 二維數組參數:第一維可省略,第二維必須給定
  • 字符數組以 '\0' 結尾,區別於空字符填充
  • &a == a:數組名即首元素地址
  • 函數指針作參數:回調機制基礎

二、面向對象核心

類 vs 對象

  • 類:抽象模板,不佔用對象內存
  • 對象:具體實例,佔用存儲空間 = 非靜態數據成員大小之和(含對齊填充)
  • 成員函數不佔用對象空間,共享代碼段

this 指針

非靜態成員函數隱含參數,指向調用對象。編譯器將 obj.func() 轉為 func(&obj)。

構造/析構順序

  1. 全局對象:`main` 前構造,`main` 返回/`exit` 時逆序析構(棧式)
  2. 局部對象:進作用域構造,出作用域逆序析構
  3. static 局部對象:首次調用構造,程序結束析構(單例模式基礎)

const 參數傳遞

void func(const Type& obj); // 推薦:避免拷貝,保護數據
void func(const Type* ptr);   // 同理

new 失敗處理

標準 new 拋 std::bad_alloc,可用 nothrow 版本返回 nullptr。

靜態成員實現數據共享

class Shared {
    static int count; // 聲明
    static void Show(); // 只能訪問靜態成員
};
int Shared::count = 0; // 定義初始化(源文件)

友元特性

  • 可為普通函數或其他類成員函數
  • 單向、不可傳遞、不可繼承
  • 打破封裝,慎用

三、繼承與派生

構造/析構不繼承

派生類需自定構造/析構,**構造時先調用基類構造**(按繼承聲明順序),析構逆序。

虛基類解決菱形繼承

class A { int a; };
class B : virtual public A {}; // 虛繼承
class C : virtual public A {};
class D : public B, public C {}; // D 中只有一份 A::a

虛基類表指針增加對象大小,訪問間接性略降性能。

類的組合

以類對象作數據成員,構造順序:成員對象構造 → 本類構造。

四、多態與虛函數

靜態 vs 動態多態

  • 靜態:函數重載/模板/運算符重載(編譯期綁定)
  • 動態:虛函數覆蓋(運行期綁定)

虛函數表機制

  • 含虛函數的類生成 **vtable**(靜態常量數組,存虛函數地址)
  • 每個對象含 **vptr** 指向類的 vtable
  • 構造函數中初始化 vptr(基類構造→基類 vptr,派生構造→派生 vptr)
  • 調用 ptr->virt() → ptr->vptr[index]()

虛析構必要性

Base* p = new Derived;
delete p; // Base::~virtual() 確保調用 Derived::~() 再 Base::~()

純虛函數與抽象類

class Interface {
    virtual void Do() = 0; // 純虛
    virtual ~Interface() = default; // 介面類必備虛析構
};

五、多態實現底層細節

  1. 虛函數在基類聲明後,所有派生類同名函數自動為虛
  2. vptr 在**構造函數**中初始化,構造期間調用虛函數屬於未定義行為(vptr 尚未指向派生 vtable)
  3. 對象內存佈局:[vptr][基類成員][派生類成員]
  4. 多重繼承含多個 vptr,虛繼承引入 vbptr/vbtable

經典面試題

Q: 構造函數能否為虛函數?
A: 不能。構造時對象類型尚未確定,vptr 未初始化完成,無法動態分發。

Q: 析構函數為何必須虛?
A: 基類指針刪除派生對象時,需動態調用派生析構釋放資源,再調用基類析構。

Q: 虛函數調用開銷?
A: 額外一次間接跳轉(vptr→vtable→函數),現代 CPU 分支預測極佳,可忽略。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved