2010-11-03 71 views
1

我正在使用類表繼承實現類型層次結構。但是,我在返回基類型而不是子類型的靜態方法時遇到了問題。我找到了解決辦法,但它不太漂亮。看看下面的類使用Castle ActiveRecord類表繼承在派生類上調用FindAll

public class Entity : ActiveRecordBase<Entity> { } 
public class Person : Entity {} 

調用

Person.FindAll(); 

實際返回的人[]實體[]代替。我可以通過在所有派生類中實現FindAll來解決這個問題,但是誰願意這樣做呢?我還能夠創建一個基類,所有的類都是從派生並實現

public R[] FindAll<R>() {} 

,但我只是不喜歡的

Person.FindAll<Person>() 

一下有什麼辦法能夠調用的FindAll ()從派生類,實際得到派生類而不是基類?

回答

4

這就是.net的工作原理:靜態方法沒有多態性。您已經找到了幾個解決方法,另一個是而不是依靠這些從ActiveRecordBase<T>繼承的靜態方法,但是直接使用ActiveRecordMediator<T>

0

也許你可以這樣做:

public class Entity<T> : ActiveRecordBase<T> { } 
public class Person : Entity<Person> {} 

這樣FindAll()將返回Person[]

+0

這個問題是你不能映射實體''作爲它是一個開放的泛型類。 – 2010-11-03 23:03:42

+0

我之前使用過這種模式,其中實體將用於保存一些常用的值(例如:id)和方法,並作爲所有實體的共同祖先。我不明白你爲什麼想要映射它。 – gcores 2010-11-03 23:09:39

+0

@gcores:所以你可以把實體的屬性放在一個單獨的類中。 – 2010-11-03 23:13:40

0

即使是Castle.ActiveRecord使用您找到解決方法的文檔。

看到這裏一個完整的例子和一些其他的解決方案:http://docs.castleproject.org/Default.aspx?Page=Type%20hierarchy&NS=Active%20Record

我複製的情況下,該網站消失的代碼。

基類 「實體」

using Castle.ActiveRecord; 

[ActiveRecord("entity"), JoinedBase] 
public class Entity : ActiveRecordBase 
{ 
    private int id; 
    private string name; 
    private string type; 

    public Entity() 
    { 
    } 

    [PrimaryKey] 
    private int Id 
    { 
     get { return id; } 
     set { id = value; } 
    } 

    [Property] 
    public string Name 
    { 
     get { return name; } 
     set { name = value; } 
    } 

    [Property] 
    public string Type 
    { 
     get { return type; } 
     set { type = value; } 
    } 

    public static void DeleteAll() 
    { 
     DeleteAll(typeof(Entity)); 
    } 

    public static Entity[] FindAll() 
    { 
     return (Entity[]) FindAll(typeof(Entity)); 
    } 

    public static Entity Find(int id) 
    { 
     return (Entity) FindByPrimaryKey(typeof(Entity), id); 
    } 
} 

派生類 「人」 和 「公司」

using Castle.ActiveRecord; 

[ActiveRecord("entitycompany")] 
public class CompanyEntity : Entity 
{ 
    private byte company_type; 
    private int comp_id; 

    [JoinedKey("comp_id")] 
    public int CompId 
    { 
     get { return comp_id; } 
     set { comp_id = value; } 
    } 

    [Property("company_type")] 
    public byte CompanyType 
    { 
     get { return company_type; } 
     set { company_type = value; } 
    } 

    public new static void DeleteAll() 
    { 
     DeleteAll(typeof(CompanyEntity)); 
    } 

    public new static CompanyEntity[] FindAll() 
    { 
     return (CompanyEntity[]) FindAll(typeof(CompanyEntity)); 
    } 

    public new static CompanyEntity Find(int id) 
    { 
     return (CompanyEntity) FindByPrimaryKey(typeof(CompanyEntity), id); 
    } 
} 

[ActiveRecord("entityperson")] 
public class PersonEntity : Entity 
{ 
    private int person_id; 

    [JoinedKey] 
    public int Person_Id 
    { 
     get { return person_id; } 
     set { person_id = value; } 
    } 

    public new static void DeleteAll() 
    { 
     DeleteAll(typeof(PersonEntity)); 
    } 

    public new static PersonEntity[] FindAll() 
    { 
     return (PersonEntity[]) FindAll(typeof(PersonEntity)); 
    } 

    public new static PersonEntity Find(int id) 
    { 
     return (PersonEntity) FindByPrimaryKey(typeof(PersonEntity), id); 
    } 
}