[英]How can I get a class that takes generic type, to call a method from an instance of that type?
我有一個使用以下方法的“ Entity”基類(我沒有實現IEquatable,這很麻煩,所以我放棄了這種方法)
virtual public bool Equals(Entity entity)
{
throw new Exception("The base Entity.Equals method should never be called");
}
我有幾個擴展Entity的類。 每個人都會實現一個Equals方法,就像這樣。
virtual public bool Equals(TestPlan other)
{
if (this.TestPlanType.Equals(other.TestPlanType) &&
this.Name.Equals(other.Name) &&
this.Description.Equals(other.Description) &&
this.DatetimeCreated.Equals(other.DatetimeCreated) &&
this.UserNameCreated.Equals(other.UserNameCreated) &&
this.Duration.Equals(other.Duration) &&
this.Scenarios.SequenceEqual(other.Scenarios)) return true;
return false;
}
我真的很想讓輸入的類型為TestPlan而不是Object。 (至少我認為我願意,我不想失去強類型)。
我意識到此方法不會“覆蓋”基類,因為我將其設置為虛擬公共而不是公共覆蓋。
我有一個采用通用類型的方法,該方法將調用.Equals()
public int GetIdenticalEntityId<T>(T entity) where T : Entity
{
List<T> exitingEntities = LoadEntities<T>();
foreach (T existingEntity in exitingEntities)
{
if (existingEntity.Equals(entity))
{
return existingEntity.Id;
}
}
return -1;
}
問題是exitingEntity.Equals()調用基類.Equals。
我如何獲得一個采用通用類型的類,以從該類型的實例中調用方法?
只需重寫基本的Equals(object other)
方法。 很簡單。
您甚至可以通過在Entity
類中聲明以下內容來使其成為必需的:
public override abstract bool Equals(object other);
public override abstract int GetHashCode();
現在,在您的類中, Equals
方法將如下所示:
public override bool Equals(object obj)
{
var other = obj as TestPlan;
if (other == null)
return false;
if (ReferenceEquals(other, this))
return true;
return this.TestPlanType.Equals(other.TestPlanType) &&
this.Name.Equals(other.Name) &&
this.Description.Equals(other.Description) &&
this.DatetimeCreated.Equals(other.DatetimeCreated) &&
this.UserNameCreated.Equals(other.UserNameCreated) &&
this.Duration.Equals(other.Duration) &&
this.Scenarios.SequenceEqual(other.Scenarios));
}
現在,如果您想實現IEquatable<T>
,它將非常簡單:
public bool Equals(TestPlan obj)
{
return Equals((object)obj);
}
您也可以通過其他方式進行此操作:
public override bool Equals(object obj)
{
return Equals(obj as TestPlan);
}
public bool Equals(TestPlan obj)
{
if (obj == null)
return false;
// Same code as before
}
哦,您也應該實現GetHashCode
以避免令人討厭的意外:
public override int GetHashCode()
{
var hash = TestPlanType.GetHashCode();
hash = (hash * 397) ^ Name.GetHashCode();
hash = (hash * 397) ^ Description.GetHashCode();
hash = (hash * 397) ^ DatetimeCreated.GetHashCode();
hash = (hash * 397) ^ UserNameCreated.GetHashCode();
hash = (hash * 397) ^ Duration.GetHashCode();
hash = (hash * 397) ^ Scenarios.GetHashCode();
return hash;
}
這真的很重要。 例如,您團隊中的某人可能有一天想將您的對象用作字典中的鍵。 如果您從一開始就正確實現GetHashCode
函數,則將在以后的代碼中避免此類陷阱。 這對於今天避免將來使用大型WTF來說是一個很小的代價。
到這里,這就是您真正需要的。
為了覆蓋一個函數,參數必須是同一時間。 因此,您的TestPlan.Equals應該類似於:
override public bool Equals(Entity entity)
{
TestPlan other = entity as TestPlan;
if (other == null)
return false;
if (this.TestPlanType.Equals(other.TestPlanType) &&
this.Name.Equals(other.Name) &&
this.Description.Equals(other.Description) &&
this.DatetimeCreated.Equals(other.DatetimeCreated) &&
this.UserNameCreated.Equals(other.UserNameCreated) &&
this.Duration.Equals(other.Duration) &&
this.Scenarios.SequenceEqual(other.Scenarios)) return true;
return false;
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.