[英]Generic type casting using Activator.CreateInstance
我有一个界面
public interface ISomething<TValue>
where TValue : IConvertible
{
...
}
然后,我还有一些具有泛型方法的非泛型类:
public class Provider
{
public static void RegisterType<TValue>(ISomething<TValue> instance)
where TValue : IConvertible
{
...
}
}
直到我要在我的特定程序集中自动注册所有适用的类型之前,这似乎还不错。
public void InitializeApp()
{
foreach(Type t in Assembly.GetExecutingAssembly().GetTypes().Where(t => typeof(ISomething<>).IsAssignableFrom(T)))
{
// ERROR
Provider.RegisterType(Activator.CreateInstance(t));
}
}
此代码导致错误,因为无法从用法中推断出参数类型。 我要么
RegisterType
提供显式的通用类型(由于代码的动态性质,我不认为可以做到这一点)或 Activator.CreateInstance
为适当的类型,以便可以从用法中推断出参数类型 但是我也不知道该怎么办? 也许还有我不知道的第三种选择。
泛型是编译时的功能,这意味着必须在编译时知道泛型类型。 因此,当您仅在运行时知道类型时,就不能使用RegisterType
方法,因为编译器无法推断出通用参数。
您在这里有几个选择。 您可以使用反射来调用正确版本的RegisterType
(如注释中所建议),或者可以创建RegisterType
的其他非泛型重载,该重载接受对象并从中找出执行时类型。
对于前者,它看起来像这样:
public void InitializeApp()
{
foreach(Type t in Assembly.GetExecutingAssembly().GetTypes().Where(t => typeof(ISomething<>).IsAssignableFrom(T)))
{
var methodInfo = typeof( Provider ).GetMethod( "RegisterType", BindingFlags.Static );
var registerTypeMethod = methodInfo.MakeGenericMethod( t );
registerTypeMethod.Invoke( null, new[] { Activator.CreateInstance(t) } );
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.