C++多檔案程式設計是什麼

2020-07-16 10:05:22
在前面的教學中,我們都是將所有的程式碼寫到一個原始檔裡面,例如:
//main.cpp
#include <iostream>
using namespace std;

class Student{
public:
    char *name;
    int age;
    float score;

    void say(){
        cout<<name<<"的年齡是"<<age<<",成績是"<<score<<endl;
    }
};

int main(){
    Student *pStu = new Student;
    pStu -> name = "小明";
    pStu -> age = 15;
    pStu -> score = 92.5f;
    pStu -> say();
    delete pStu;  //刪除物件
    return 0;
}

如上所示,所有的程式碼都位於 main.cpp 檔案中。對於程式碼量幾十行或者幾百行的小程式,這或許無可厚非,但當程式膨脹程式碼到幾千行甚至上萬行後,就應該考慮將程式碼“分散”到多個檔案中。注意這裡所謂的“分散”,並不是胡亂地劃分。為了方便後期的維護,分散程式碼應遵循一個基本原則:實現相同功能的程式碼應儲存在一個檔案中。


事實上,一個完整的 C++ 專案常常是由多個程式碼檔案組成的,根據字尾名的不同,大致可以將它們分為如下 2 類:
  1. .h 檔案:又稱“標頭檔案”,用於存放常數、函數的宣告部分、類的宣告部分;
  2. .cpp 檔案:又稱“原始檔”,用於存放變數、函數的定義部分,類的實現部分。

實際上,.cpp 檔案和 .h 檔案都是原始檔,除了字尾不一樣便於區分和管理外,其他的幾乎相同,在 .cpp 中編寫的程式碼同樣也可以寫在 .h 中。之所以將 .cpp 檔案和 .h 檔案在專案中承擔的角色進行區別,不是 C++ 語法的規定,而是約定成俗的規範,讀者遵守即可。

雖然類內部的成員函數可以在宣告的同時進行定義(自動成為行內函式),但原則上不推薦這樣使用。也就是說,即便定義成員函數的程式碼很少,其定義也應該放在適當的 .cpp 檔案中。

另外對於一些系統提供的庫,出於版權和保密的考慮,大多是已經編譯好的二進位制檔案,其中可能僅包含 .h 檔案,而沒有 .cpp 檔案。

以上面程式為例,在實際場景中,我們應該將其做如下劃分:
//student.h
class Student {
public:
    const char *name;
    int age;
    float score;
    void say();
};

//student.cpp
#include <iostream>   //std::cout、std::endl
#include "student.h"  //Student
void Student::say() {
    std::cout << name << "的年齡是" << age << ",成績是" << score << std::endl;
}

//main.cpp
#include "student.h"  //Student
int main() {
    Student *pStu = new Student;
    pStu->name = "小明";
    pStu->age = 15;
    pStu->score = 92.5f;
    pStu->say();
    delete pStu;  //刪除物件
    return 0;
}
此專案的目錄結構如下:
專案─┐
      ├ student.h
      ├ student.cpp
      └ main.cpp
執行結果為:

小明的年齡是15,成績是92.5

如上所示,在對之前的程式進行合理地劃分時,需要額外將 "student.h" 分別引入到 student.cpp 檔案和 main.cpp 檔案中,理由很簡單,因為這 2 個檔案中需要使用 student.h 檔案宣告的 Student 類,就如同我們在使用 cin 和 cout 時需要提前引入 <iostream> 標頭檔案一樣。

注意,引入編譯器自帶的標頭檔案(包括標準標頭檔案)用尖括號,例如 <iostream>;引入自定義的標頭檔案用 "" 雙引號,例如 "student.h"。

可以看到,之前的一段程式被劃分到了 3 個檔案中,其中:
  • student.h 標頭檔案負責儲存 Student 類的宣告部分;
  • student.cpp 檔案負責儲存 Student 類中成員函數的定義部分;
  • main.cpp 檔案負責儲存主程式(main() 函數)。

經過上面這樣劃分,當後期想檢視 Student 類有哪些成員時,就可以直接開啟 student.h 檔案,想檢視某個成員函數的具體實現時,可以開啟 student.cpp 檔案。

除此之外,當一個專案中的檔案過多時,還可以將它們分散儲存到不同的資料夾下。例如:
專案─┐
      ├─ include ┐
      │           ├ student.h
      │           └ ...
      ├─ source ┐
       ...        ├ student.cpp
                  ├ main.cpp
                  └ ...
如上所示,將所有的標頭檔案儲存在 include 資料夾下,將所有的 .cpp 檔案儲存在 source 資料夾下。總之專案越大,多檔案程式設計的優勢越明顯。