2016-08-02 27 views
4

我看到了一個這樣的代碼前些天:Delphi中調用的這種「循環繼承」是什麼?

type 
    TcxGridTableControllerAccess = class (TcxGridTableController); 

    TMycxGridDBTableView = class (TcxGridDBTableView) 
    protected 
     function GetViewDataClass: TcxCustomGridViewDataClass; override; 
    end; 

    TMycxGridViewData = class (TcxGridViewData) 
    protected 
     function GetFilterRowClass: TcxGridFilterRowClass; override; 
    end; 

    TMycxGridFilterRow = class (TcxGridFilterRow) 
    protected 
     procedure SetValue(Index: Integer; const Value: Variant); override; 
    end; 

    TcxGridDBTableView = class (TMycxGridDBTableView); 

TMycxGridDBTableView從TcxGridDBTableView從TMycxGridDBTableView繼承繼承。搜索循環繼承,但僅搜索Java結果。

這是什麼叫?

Ps:我沒有完整的可構建代碼。

+0

供將來參考:此處的正確行爲是編輯您的上一個問題,而不是簡單地創建新的重複問題。在這種情況下,這個更好,所以我已經關閉了另一個。 –

+0

@Ken - 只有標題是相同的。另一個問題提出了一個完全不同的東西,它顯示了一些不存在的代碼示例。當提供者無法提供適當的樣品時,顯然已經回答了好幾次。因此,這裏的問題與正確的樣本... –

+0

@SertacAkyuz:查看其他問題的修訂歷史。他們是同一個問題。 OP在那裏得到了降低,並且在這裏再次提出了同樣的問題,稍微提供了更多信息以及另一篇文章中應該使用的代碼(曾經存在過)。羅布甚至在那裏寫了基本相同的答案。 –

回答

6

你顯示的不是循環繼承。會發生什麼是dxSample.TMycxGridDBTableView繼承自另一個單位的TcxGridDBTableView,可能是cxGridDBTableView.TcxGridDBTableView。並且dxSample.TcxGridDBtableView繼承自dxSample.TMycxGridDBTableView

您的代碼就相當於:

type 
    TcxGridTableControllerAccess = class(TcxGridTableController); 

    { Note: this does NOT inherit from the TcxGridDBTableView defined } 
    { a little further on in the source. It inherits from the original } 
    { DevEx TcxGridDBTableView.          } 

    TMycxGridDBTableView = class(cxGridDBTableView.TcxGridDBTableView) 
    protected 
    function GetViewDataClass: TcxCustomGridViewDataClass; override; 
    end; 

    TMycxGridViewData = class(TcxGridViewData) 
    protected 
    function GetFilterRowClass: TcxGridFilterRowClass; override; 
    end; 

    TMycxGridFilterRow = class(TcxGridFilterRow) 
    protected 
    procedure SetValue(Index: Integer; const Value: Variant); override; 
    end; 

    TcxGridDBTableView = class(TMycxGridDBTableView); 

所以層次是:

cxGridDBTableView.TcxGridDBTableView 
       | 
       v 
    dxSample.TMycxGridDBTableView 
       | 
       v 
    dxSample.TcxGridDBTableView 

所以dxSample.TMycxGrdiDBTableView繼承dxSample.TcxGridDBTableView,但是從cxGridDBTableView.TcxGridDBTableView代替,所以沒有那麼那裏稱爲循環繼承。整個誤解來自於這樣的事實,即不同單位中的兩個類具有相同的名稱,並且第一個聲明不能完全限定它繼承的類。

現在,如果有人把單位dxSamplecxridDBTableView後,他或她的uses條款,然後dxSample.TCxGridDBTableView是用來代替原來的DevEx類。這被稱爲插入

當人們想要修改的VCL和FireMonkey的行爲,這是不尋常看到這樣

type 
    TVCLClass = class(OriginalVCLUnit.TVCLClass) 
    // modifications to the original TVCLClass 
    end; 

type 
    TMyVCLClass = class(OriginalVCLUnit.TVCLClass) 
    // 
    end; 

    TVCLClass = class(TMyVCLCLass); 

你確實顯示出後者的代碼中介類。

9

示例代碼不會執行您認爲的操作。您看到TMycxGridDBTableView被定義爲TcxGridDBTableView的後代,然後您看到TcxGridDBTableView,定義爲TcxGridDBTableView的後代。

但是,您在頂部看到的TcxGridDBTableView與您稍後會看到的TcxGridDBTableView不一樣。第一個是指在別處宣佈的一個類別,在其他單位中。接下來的事件是聲明一個新的這個碰巧與其他單元的類名相同的單元。

該技術被稱爲中介片類別。它用於引入新的GetViewDataClass方法,但仍以相同的類名結束。使用該名稱的控件的表單將使用該類的新版本而不是原始版本。這是一種自定義VCL控件的方法,無需編譯和安裝定製軟件包。