2017-10-11 47 views
3

我有一個通用的類定義如下paramater的基:確保上通用的方法的參數是在同一類

public abstract class BaseValidator<T> : IValidator<T> where T: IEntity 
{ 
    //some methods and parameters here 
    protected void Include<E>(IValidator<E> validator) where E : class , IEntity 
    { 
     if (typeof(E) != typeof(T).BaseType) 
     { 
      throw new ArgumentException($"Generic class Validator<T> must only Include Validators for base classes"); 
     } 
     //Some business logic around connecting validators 
    } 
} 

的方法,包括被設計爲採取在一個驗證參數,它使用此結合驗證彼此相似,類似於驗證者的責任鏈。我目前有運行時檢查,以確保E是T的基類,但我想移動它來編譯時間檢查。

我試圖在第二個加where子句的方法包括如下:

where T:E 

但是Visual Studio中抱怨說,該方法包括沒有定義類型參數「T」

如果我定義了一個類型參數,我得到一個消息,指出類型參數'T'與外部類的類型參數具有相同的名稱。

如何確保傳入我的方法的泛型類型是我的T實現的基類?


編輯1:

public class BankAccountValidator : BaseValidator<BankAccount> 
    { 
     public BankAccountValidator(IValidator<OwnedProduct> validator) 
     { 
      Include(validator); 
      //Some logic here 
     } 
    } 

在這種情況下實現的BankAccount OwnedProduct。因此,當在BankAccount上調用驗證方法時,它也會調用OwnedProduct上的驗證方法。

我想強制您不能將BankAccountValidator傳遞給另一個BankAccountValidator,或者如果我有一個OwAccredit類型,該BankAccount並不是從中派生出來的,我無法將OwnedCreditValidator傳遞給構造函數。

有大量的驗證器,並強烈鍵入這樣會阻止我運行到運行時問題。

+0

你不能在該方法限制類級別類型參數類,甚至沒有多大意義。假設你能夠做到這一點,現在'T'應該從'E'繼承。然後你添加一個帶有某個類型參數'F'的方法,並且說'T'應該從它繼承。現在'T'應該繼承'E'和'F'。 – Evk

+1

如果我理解正確,您應該可以將方法簽名更改爲'protected void Include(IValidator validator){...}'?因爲'T'已經定義好了嗎?雖然可能沒有得到它。 – thmshd

+0

好吧,我刪除了我的答案,因爲我之前沒有得到您的問題。 – thmshd

回答

2
public abstract class BaseValidator<T, E> : IValidator<T> 
    where E: IEntity 
    where T: E 
{ 
    //some methods and parameters here 
    protected void Include(IValidator<E> validator) 
    {   
     //Some business logic around connecting validators 
    } 
} 

public class BankAccountValidator : BaseValidator<BankAccount, OwnedProduct> 
{ 
    public BankAccountValidator(IValidator<OwnedProduct> validator) 
    { 
     Include(validator); 
     //Some logic here 
    } 
} 

如果OwnedProductValidator可以驗證自己的話:

public class OwnedProductValidator : IValidator<OwnedProduct> 
{ 
    // IValidator interface implementation 
} 

public class Program 
{ 
    public static void Main() 
    { 
     var ownedProductValidator = new OwnedProductValidator();     
     var bankAccountValidator = new BankAccountValidator(ownedProductValidator); 
    } 
} 

如果OwnedProductValidator需要一些其他類的驗證,則:

public class OwnedProductValidator : BaseValidator<OwnedProduct, SomeOtherClass>{} 
+0

然後,我會如何使用BaseValidator爲我的基類?OwnedProductValidator的第二個參數是什麼? – ObiEff

+1

對不起,我跟蹤了另一個問題,忘記標記爲答案。而不是完全按照你的代碼,我離開了基本驗證器,並創建了一個實現Base驗證器並具有繼承限制的輔助類。謝謝 – ObiEff

相關問題