有時候我們需要提供對外的api,通常會以標頭檔案的形式提供。舉個簡單的例子:
提供乙個從某個指定數開始列印的介面,標頭檔案內容如下:
#ifndef _test_api_h#define _test_api_h
//test_api.h
class testapi
void testprint(int num);
private:
int start_ = 0;
};#endif //_test_api_h
實現檔案如下:
#include "test_api.h"
#include //test_api.cc
testapi::testprint(int num);
test_api.testprint(15);
return 0;
}從前面的內容來看, 一切都還正常,但是有什麼問題呢?
第一點可以很明顯的看出來,其中的私有變數star_能否在標頭檔案中看到,如果實現越來越複雜,這裡可能也會出現更多的私有變數。有人可能會問,私有變數外部也不能訪問,暴露又何妨?
不過你只是提供幾個介面,給別人看到這麼多資訊幹啥呢?這樣就會導致實現和介面耦合在了一起。
另外一方面,如果有另外乙個庫使用了這個庫,而你的這個庫實現變了,標頭檔案就會變,而標頭檔案一旦變動,就需要所有使用了這個庫的程式都要重新編譯!
這個代價是巨大的。
所以,我們應該盡可能地保證標頭檔案不變動,或者說,盡可能隱藏實現,隱藏私有變數。
pointer to implementation,由指標指向實現,而不過多暴露細節。廢話不多說,上**:
#ifndef _test_api_h#define _test_api_h
#include //test_api.h
class testapi;
#endif //_test_api_h
從這個標頭檔案中,我們可以看到:
我們再來看下具體的實現:
#include "test_api.h"#include //test_api.cc
class testapi::testimpl
testimpl() = default;
~testimpl() = default;
private:
int start_;
};void testapi::testimpl::testprint(int num)
//注意,析構函式需要
testapi::~testapi() = default;
從實現中看到,testapi中的testprint呼叫了testimpl中的testprint實現,而所有的具體實現細節和私有變數都在testimpl中,即便實現變更了,其他庫不需要重新編譯,而僅僅是在生成可執行檔案時重新鏈結。
從例子中,我們可以看到pimpl模式中有以下優點:
當然了,由於實現在另外乙個類中,所以會多一次呼叫,會有效能的損耗,但是這點幾乎可以忽略。
為何優先選用unique_ptr而不是裸指標?
認真理一理c++的建構函式
這才是現代c++單例模式簡單又安全的實現
隱藏struct具體實現細節
我們知道對於struct,其所有的成員預設情況下是所有對外可見的,即為public屬性。但是有時候為了提高程式的封裝性,我們需要將struct的內容細節隱藏起來,怎麼做呢?可以使用下面這種做法達到目的。a.h typedef struct a at class test a.cpp include ...
介面的實現
1 介面的實現 class 類名 implements 介面1,介面2,介面3 方法1 方法2 介面實現的注意事項 1 為介面中所有的方法提供具體的實現。2 必須遵守重寫的所有規則。重寫的規則 1 子類的重寫方法不能丟擲更大的異常 2 子類的重寫方法不能有更小的訪問範圍 父類 public void...
C 介面 介面的實現
c 定義了介面後,就要在子類中實現。c 中通常把子類和父類的關係稱為繼承,子類和介面的關係稱為實現。子類可以繼承乙個父類,可以實現多個介面。介面中不能定義建構函式,所以介面不能例項化。下面我們看例子 using system public inte ce ichoose public class t...