我有一个基本的抽象类及其抽象类型参数为:
public abstract class Database<T> where T : DatabaseItem, new() {
protected List<T> _items = new List<T> ();
protected virtual void Read (string[] cols) {
T item = new T ();
...
}
public abstract class DatabaseItem {
...
}
然后,我得到了一些固有的子类:
public class ShopDatabase : Database<ShopItem> {}
public class ShopItem : DatabaseItem {}
public class WeaponDatabase : Database<WeaponItem> {}
public class WeaponItem : DatabaseItem {}
...
现在,我想放置一个Dictionary来跟踪数据库,并使用DatabaseItem类型来返回它们的方法,如下所示:
Dictionary<Type, Database<DatabaseItem>> databases;
public static Database<T> GetDatabase<T> () where T: DatabaseItem {
return databasebases [typeof (T)];
}
然后它给了我“”,因为数据库项是抽象的,所以“T”必须是具有公共(public)无参数构造函数的非抽象类型,才能将其用作参数“T”。错误。我将DatabaseItem设为非抽象类型,该错误消失了,但是仍然出现了很多类型转换错误...
找到了类似的question,但我还是不明白...
有什么更好的解决方案/结构来实现这一目标?
最佳答案
最简单的方法是将Database<T>
后代存储为对象:
static class DatabaseManager
{
private static Dictionary<Type, object> databases = new Dictionary<Type, object>();
// ....
public static Database<T> GetDatabase<T>()
where T : DatabaseItem, new()
{
return (Database<T>)databases[typeof(T)];
}
}
即使使用无参数构造函数将
DatabaseItem
转换为非抽象类,这也无济于事,因为typeof(Database<ShopItem>) != typeof(Database<DatabaseItem>)
。注意,
GetDatabase<T>
方法的一般约束必须与Database<T>
类相同。更新。
使用反射:
var databaseItemType = typeof(ShopDatabase).BaseType.GetGenericArguments()[0];
对于这样的情况:
class FooDatabase : Database<FooItem> {}
class BooDatabase : FooDatabase {}
// etc...
您将需要遍历继承树以找到
Database<FooItem>
。关于c# - 处理类继承自抽象类和类型参数,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/34305723/