天天看點

不要重複發明輪子:C++重用的5重境界(4)——繼承接口DLL

第四重境界:繼承接口dll

看起來“代理接口dll”已經能夠很好的完成任務了,但追求完美的你是否總覺得有的地方不夠優美呢?

關鍵就在于這部分:

interfaceclass:: function1(int param1, char param2 ){

    return m_prealizeclass-> function1(param1, param2 );

}

以上這段代碼是代理模式的一種實作方法,但也有它的不足之處:對于realizeclass的函數,interfaceclass都要寫一個函數,每個函數的寫法都是一樣的:

return m_prealizeclass-> functionxxx(param1, param2 ……………..);

對于隻有幾個方法的類來說,這可能沒有什麼,但是如果realizeclass類有幾十上百個方法,那interfaceclass就有幾十上百個這樣類似的函數,看起來是不是很暈呢?

有沒有一種方法能夠不用寫這麼多的無聊的函數呢?有,這就是本章要介紹的“繼承接口dll”。我們還是按照第三重境界的方法來解釋這個方法:

繼承:就是面向對象的繼承概念

接口:就是java中的interface一個概念;

dll:就是動态連結庫了:)

翻譯成一句話就是:dll通過繼承的方法對外提供接口

如果你還記得第三重境界的實作方式,一對比就會發現,這兩個方法其實大同小異,關鍵就是具體的實作方式不一樣:一個通過代理模式,一個通過繼承方式。那麼我們就來看看這個繼承方式具體如何實作。

/*******************************dll代碼聲明部分開始**********************/

class interfaceclass{    //聲明接口類,無成員資料,隻有方法,這裡不用dllexport聲明,//為什麼呢,請自行查閱相關資料?

    public:

    void function1(int param1, char param2 ) = 0 //聲明為純虛函數,子類必須改寫;

    void function2(int param1 = 0 ;

    void function3(bool param1, char param2 ) = 0 ;

class realizeclass::public interfaceclass{ //繼承接口類,函數必須改寫

       //成員變量

       …………………………………..

       //繼承的函數,需要重寫。

    void function1(int param1, char param2 );

    void function2(int param1 );

    void function3(bool param1, char param2 ) ;

//這兩個函數是“繼承接口dll”實作關鍵,後面介紹為什麼。

extern interfaceclass* g_interfaceclassptr ; //不要和下面的extern混淆哈:)

extern “c” interfaceclass* __decspec(dllexport)  createinterfaceclass();

extern “c” interfaceclass* __decspec(dllexport)  deleteinterfaceclass();

/******************************* dll代碼聲明部分結束**********************/

/*******************************dll代碼定義部分開始**********************/

void realizeclass::function1(){

       //函數具體實作,do what you want!!!

    ……………………………..

void realizeclass::function2(){

void realizeclass::function3(){

interfaceclass* g_interfaceclassptr = null;

interfaceclass* createinterfaceclass(){

   if(g_interfaceclassptr == null){

       g_interfaceclassptr = new realizeclass(); //生成的是具體的類

return g_interfaceclassptr;

interfaceclass* deleteinterfaceclass(){

     delete g_interfaceclassptr;

     g_interfaceclassptr = null;

/*******************************dll代碼定義部分結束**********************/

/***************************使用dll的用戶端代碼********************/

interfaceclass* pinterfaceclass = createinterfaceclass();

pinterfaceclass->function1(param1, param2);

………………………………………………………

deleteinterfaceclass();

樣例代碼到這裡就結束了,我們來總結一下這種方法的關鍵實作點:

1)實作類繼承接口類,而不是“代理接口dll”中的接口類包含實作類的指針(uml中的聚合aggregation的一種實作方式);

2)由于第一條的存在,使得用戶端不能直接new某個對象,是以要通過createinterfaceclass來建立一個具體的實作類。

3)由于第二條建立了實作類,為了避免記憶體洩漏,是以要deleteinterfaceclass。

 ========未完待續,後面更精彩===========