[英]Getting warning, 'Type Parameter X Hides Interface X'
這是在Visual Studio 2010中發生的。
我正在使用通用方法,並且基本上失去了智能,使我無法繼續從事該項目。
我基本上有以下課程:
public class SearchRepository : DataRepository<IAudit>
{
public override IEnumerable<IAudit> RetrieveAll<IAuditSearch>(IAuditSearch searchParameters)
{
// CODE GOES HERE
}
public override bool Delete<TIAudit>(IAudit audit)
{
// CODE GOES HERE
}
}
這繼承自:
public abstract class DataRepository<T>
{
public virtual IEnumerable<T> RetrieveAll<U>(U parameter1)
{
throw new NotImplementedException();
}
public virtual bool Delete<U>(U parameter1)
{
throw new NotImplementedException();
}
}
所以Delete的工作方式與我期望的完全一樣。 我有智能感知,它可以正確編譯。 使用IAuditSearch,RetrieveAll無法正常工作。 如果將其更改為TIAuditSearch,則表示“沒有合適的方法可以覆蓋”。
不知道我在做什么錯,但是絕對對我不滿意。
更新:將虛擬更改為覆蓋頂部的Delete方法。 那是個錯誤。
您隱式隱藏(不覆蓋)方法的簽名
bool Delete<myType>(myType param) { ... }
您可以通過在派生類的Delete屬性上引入“ new”關鍵字來克服該錯誤。 這明確地隱藏了簽名,並使每個人高興,因為它說明了您的意圖。
請閱讀Microsoft文檔, 網址為: http : //msdn.microsoft.com/zh-cn/library/aa691135%28v=vs.71%29.aspx 。
您無法定義方法公共重寫IEnumerable RetrieveAll(IAuditSearch searchParameters)
該方法仍必須使用U類型參數代替IAuditSearch。 由呼叫者選擇要傳遞的類型。
您可能需要創建一個ISearch接口,並在基類上添加U:ISearch位置,但是即使那樣,您的子類也需要接受所有ISearch實現,而不僅僅是IAuditSearch。
最好的解決方案可能是定義一個IAuditSearch存儲庫,該存儲庫定義了RetreiveAll方法。
編輯:我看到問題已經改變。 您現在在兩種方法上都有相同的問題; 您無法指定覆蓋該方法時要使用哪個接口,必須維護通用類型參數。
public override IEnumerable<T> RetrieveAll<U>(U parameter1) { }
public override bool Delete<U>(U parameter1) { }
注意,您也不能在方法中添加where子句。 這打破了Liskov換人原則 。 另外,我什至不確定編譯器是否允許您這樣做。
不幸的是,確切的上下文對我來說還不太清楚,但我相信您的代碼應如下所示:
public interface IParameter<T> {
bool Match(T entry);
}
public abstract class DataRepository<T, TParameter>
where TParameter : IParameter<T> {
public abstract IEnumerable<T> RetrieveAll(TParameter parameter1);
public abstract bool Delete(TParameter parameter1);
}
//
public interface IAudit {/* ... */}
public interface IAuditSearch : IParameter<IAudit> {/* ... */}
public class SearchRepository : DataRepository<IAudit, IAuditSearch> {
public override bool Delete(IAuditSearch parameter1) {
// iterate by collection items using parameter matching
// CODE GOES HERE (DELETE ALL FOUND ENTRIES)
}
public override IEnumerable<IAudit> RetrieveAll(IAuditSearch parameter1) {
// iterate by collection items using parameter matching
// CODE GOES HERE (RETURN ALL FOUND ENTRIES)
}
}
不同的IAuditSearch實現將封裝“按不同參數搜索”邏輯:
var guidSearchResult = repository.RetrieveAll(
new GuidSearch(new Guid("00000000-0000-0000-0000-000000000000")));
var idRangeSearchResult = repository.RetrieveAll(
new IDRangeSearch(1000, 2000));
GuidSearch和IDRangeSearch的實現方式為:
public class GuidSearch : IAuditSearch {
Guid ID;
public GuidSearch(Guid id) {
this.ID = id;
}
public bool Match(IAudit entry) {
/* search implementation using ID(Guid)*/
throw new NotImplementedException();
}
}
public class IDRangeSearch : IAuditSearch {
int StartID;
int EndID;
public IDRangeSearch(int startId, int endId) {
this.StartID = startId;
this.EndID = endId;
}
public bool Match(IAudit entry) {
/* search implementation using ID range (StartID...EndID)*/
throw new NotImplementedException();
}
}
下面的代碼可以代替嗎?
public class SearchRepository : DataRepository<IAudit, IAuditSearch>
{
public override IEnumerable<IAudit> RetrieveAll<IAuditSearch>(IAuditSearch searchParameters)
{
// CODE GOES HERE
}
public override bool Delete<TIAudit>(IAudit audit)
{
// CODE GOES HERE
}
}
public abstract class DataRepository<T, TSearch>
{
public virtual IEnumerable<T> RetrieveAll(TSearch parameter1)
{
throw new NotImplementedException();
}
public virtual bool Delete(T parameter1)
{
throw new NotImplementedException();
}
}
因此,對於DataRepository的每個實例,我們都聲明結果類型(T)和搜索類型(TSearch)。
-C
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.